[llvm-branch-commits] [clang] [LifetimeSafety] Introduce a liveness-based lifetime policy (PR #159991)

2025-09-24 Thread Utkarsh Saxena via llvm-branch-commits

https://github.com/usx95 updated 
https://github.com/llvm/llvm-project/pull/159991

>From 8a7ec9fe4b3e098b629102219cf52a116472e9a2 Mon Sep 17 00:00:00 2001
From: Utkarsh Saxena 
Date: Sun, 21 Sep 2025 16:30:28 +
Subject: [PATCH] liveness-based-lifetime-policy

---
 .../clang/Analysis/Analyses/LifetimeSafety.h  |  18 +-
 clang/lib/Analysis/LifetimeSafety.cpp | 461 +---
 .../test/Analysis/LifetimeSafety/benchmark.py |  82 ++-
 clang/test/Sema/warn-lifetime-safety.cpp  | 138 +++--
 .../unittests/Analysis/LifetimeSafetyTest.cpp | 501 +-
 5 files changed, 713 insertions(+), 487 deletions(-)

diff --git a/clang/include/clang/Analysis/Analyses/LifetimeSafety.h 
b/clang/include/clang/Analysis/Analyses/LifetimeSafety.h
index 512cb76cd6349..6d3e3f61446e0 100644
--- a/clang/include/clang/Analysis/Analyses/LifetimeSafety.h
+++ b/clang/include/clang/Analysis/Analyses/LifetimeSafety.h
@@ -29,7 +29,7 @@
 namespace clang::lifetimes {
 
 /// Enum to track the confidence level of a potential error.
-enum class Confidence {
+enum class Confidence : uint8_t {
   None,
   Maybe,   // Reported as a potential error (-Wlifetime-safety-strict)
   Definite // Reported as a definite error (-Wlifetime-safety-permissive)
@@ -55,6 +55,7 @@ class Fact;
 class FactManager;
 class LoanPropagationAnalysis;
 class ExpiredLoansAnalysis;
+class LiveOriginAnalysis;
 struct LifetimeFactory;
 
 /// A generic, type-safe wrapper for an ID, distinguished by its `Tag` type.
@@ -89,6 +90,7 @@ inline llvm::raw_ostream &operator<<(llvm::raw_ostream &OS, 
OriginID ID) {
 // TODO(opt): Consider using a bitset to represent the set of loans.
 using LoanSet = llvm::ImmutableSet;
 using OriginSet = llvm::ImmutableSet;
+using OriginLoanMap = llvm::ImmutableMap;
 
 /// A `ProgramPoint` identifies a location in the CFG by pointing to a specific
 /// `Fact`. identified by a lifetime-related event (`Fact`).
@@ -110,8 +112,16 @@ class LifetimeSafetyAnalysis {
   /// Returns the set of loans an origin holds at a specific program point.
   LoanSet getLoansAtPoint(OriginID OID, ProgramPoint PP) const;
 
-  /// Returns the set of loans that have expired at a specific program point.
-  std::vector getExpiredLoansAtPoint(ProgramPoint PP) const;
+  /// Returns the set of origins that are live at a specific program point,
+  /// along with the confidence level of their liveness.
+  ///
+  /// An origin is considered live if there are potential future uses of that
+  /// origin after the given program point. The confidence level indicates
+  /// whether the origin is definitely live (Definite) due to being domintated
+  /// by a set of uses or only possibly live (Maybe) only on some but not all
+  /// control flow paths.
+  std::vector>
+  getLiveOriginsAtPoint(ProgramPoint PP) const;
 
   /// Finds the OriginID for a given declaration.
   /// Returns a null optional if not found.
@@ -138,7 +148,7 @@ class LifetimeSafetyAnalysis {
   std::unique_ptr Factory;
   std::unique_ptr FactMgr;
   std::unique_ptr LoanPropagation;
-  std::unique_ptr ExpiredLoans;
+  std::unique_ptr LiveOrigins;
 };
 } // namespace internal
 } // namespace clang::lifetimes
diff --git a/clang/lib/Analysis/LifetimeSafety.cpp 
b/clang/lib/Analysis/LifetimeSafety.cpp
index 14fb945382e65..7d880ea26833b 100644
--- a/clang/lib/Analysis/LifetimeSafety.cpp
+++ b/clang/lib/Analysis/LifetimeSafety.cpp
@@ -22,6 +22,7 @@
 #include "llvm/ADT/SmallBitVector.h"
 #include "llvm/ADT/SmallVector.h"
 #include "llvm/Support/Debug.h"
+#include "llvm/Support/ErrorHandling.h"
 #include "llvm/Support/TimeProfiler.h"
 #include 
 #include 
@@ -865,29 +866,30 @@ class DataflowAnalysis {
 std::conditional_t;
 Worklist W(Cfg, AC);
+llvm::SmallBitVector Seen(Cfg.getNumBlockIDs() + 1);
 
 const CFGBlock *Start = isForward() ? &Cfg.getEntry() : &Cfg.getExit();
 InStates[Start] = D.getInitialState();
+Seen.set(Start->getBlockID());
 W.enqueueBlock(Start);
 
-llvm::SmallBitVector Visited(Cfg.getNumBlockIDs() + 1);
-
 while (const CFGBlock *B = W.dequeue()) {
   Lattice StateIn = getInState(B);
   Lattice StateOut = transferBlock(B, StateIn);
   OutStates[B] = StateOut;
-  Visited.set(B->getBlockID());
   for (const CFGBlock *AdjacentB : isForward() ? B->succs() : B->preds()) {
 if (!AdjacentB)
   continue;
 Lattice OldInState = getInState(AdjacentB);
-Lattice NewInState = D.join(OldInState, StateOut);
+bool SeeingFirstTime = !Seen.test(AdjacentB->getBlockID());
+Lattice NewInState =
+SeeingFirstTime ? StateOut : D.join(OldInState, StateOut);
 // Enqueue the adjacent block if its in-state has changed or if we have
-// never visited it.
-if (!Visited.test(AdjacentB->getBlockID()) ||
-NewInState != OldInState) {
+// never seen it.
+if (SeeingFirstTime || NewInState != OldInState) {
   InStates[AdjacentB] = NewInState

[llvm-branch-commits] [llvm] [LV] Use VPReductionRecipe for partial reductions (PR #147513)

2025-09-24 Thread Sam Tebbs via llvm-branch-commits

https://github.com/SamTebbs33 edited 
https://github.com/llvm/llvm-project/pull/147513
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] [BOLT] Gadget scanner: make use of C++17 features and LLVM helpers (PR #141665)

2025-09-24 Thread Anatoly Trosinenko via llvm-branch-commits

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

>From 9e5d66ac23bd52eb56f959812426e4acaaa58a19 Mon Sep 17 00:00:00 2001
From: Anatoly Trosinenko 
Date: Tue, 27 May 2025 21:06:03 +0300
Subject: [PATCH] [BOLT] Gadget scanner: make use of C++17 features and LLVM
 helpers

Perform trivial syntactical cleanups:
* make use of structured binding declarations
* use LLVM utility functions when appropriate
* omit braces around single expression inside single-line LLVM_DEBUG()

This patch is NFC aside from minor debug output changes.
---
 bolt/lib/Passes/PAuthGadgetScanner.cpp| 67 +--
 .../AArch64/gs-pauth-debug-output.s   | 14 ++--
 2 files changed, 38 insertions(+), 43 deletions(-)

diff --git a/bolt/lib/Passes/PAuthGadgetScanner.cpp 
b/bolt/lib/Passes/PAuthGadgetScanner.cpp
index 192b1da27759e..cfc0bc2cfc0da 100644
--- a/bolt/lib/Passes/PAuthGadgetScanner.cpp
+++ b/bolt/lib/Passes/PAuthGadgetScanner.cpp
@@ -88,8 +88,8 @@ class TrackedRegisters {
   TrackedRegisters(ArrayRef RegsToTrack)
   : Registers(RegsToTrack),
 RegToIndexMapping(getMappingSize(RegsToTrack), NoIndex) {
-for (unsigned I = 0; I < RegsToTrack.size(); ++I)
-  RegToIndexMapping[RegsToTrack[I]] = I;
+for (auto [MappedIndex, Reg] : llvm::enumerate(RegsToTrack))
+  RegToIndexMapping[Reg] = MappedIndex;
   }
 
   ArrayRef getRegisters() const { return Registers; }
@@ -203,9 +203,9 @@ struct SrcState {
 
 SafeToDerefRegs &= StateIn.SafeToDerefRegs;
 TrustedRegs &= StateIn.TrustedRegs;
-for (unsigned I = 0; I < LastInstWritingReg.size(); ++I)
-  for (const MCInst *J : StateIn.LastInstWritingReg[I])
-LastInstWritingReg[I].insert(J);
+for (auto [ThisSet, OtherSet] :
+ llvm::zip_equal(LastInstWritingReg, StateIn.LastInstWritingReg))
+  ThisSet.insert_range(OtherSet);
 return *this;
   }
 
@@ -224,11 +224,9 @@ struct SrcState {
 static void printInstsShort(raw_ostream &OS,
 ArrayRef Insts) {
   OS << "Insts: ";
-  for (unsigned I = 0; I < Insts.size(); ++I) {
-auto &Set = Insts[I];
+  for (auto [I, PtrSet] : llvm::enumerate(Insts)) {
 OS << "[" << I << "](";
-for (const MCInst *MCInstP : Set)
-  OS << MCInstP << " ";
+interleave(PtrSet, OS, " ");
 OS << ")";
   }
 }
@@ -416,8 +414,9 @@ class SrcSafetyAnalysis {
 // ... an address can be updated in a safe manner, producing the result
 // which is as trusted as the input address.
 if (auto DstAndSrc = BC.MIB->analyzeAddressArithmeticsForPtrAuth(Point)) {
-  if (Cur.SafeToDerefRegs[DstAndSrc->second])
-Regs.push_back(DstAndSrc->first);
+  auto [DstReg, SrcReg] = *DstAndSrc;
+  if (Cur.SafeToDerefRegs[SrcReg])
+Regs.push_back(DstReg);
 }
 
 // Make sure explicit checker sequence keeps register safe-to-dereference
@@ -469,8 +468,9 @@ class SrcSafetyAnalysis {
 // ... an address can be updated in a safe manner, producing the result
 // which is as trusted as the input address.
 if (auto DstAndSrc = BC.MIB->analyzeAddressArithmeticsForPtrAuth(Point)) {
-  if (Cur.TrustedRegs[DstAndSrc->second])
-Regs.push_back(DstAndSrc->first);
+  auto [DstReg, SrcReg] = *DstAndSrc;
+  if (Cur.TrustedRegs[SrcReg])
+Regs.push_back(DstReg);
 }
 
 return Regs;
@@ -868,9 +868,9 @@ struct DstState {
   return (*this = StateIn);
 
 CannotEscapeUnchecked &= StateIn.CannotEscapeUnchecked;
-for (unsigned I = 0; I < FirstInstLeakingReg.size(); ++I)
-  for (const MCInst *J : StateIn.FirstInstLeakingReg[I])
-FirstInstLeakingReg[I].insert(J);
+for (auto [ThisSet, OtherSet] :
+ llvm::zip_equal(FirstInstLeakingReg, StateIn.FirstInstLeakingReg))
+  ThisSet.insert_range(OtherSet);
 return *this;
   }
 
@@ -1036,8 +1036,7 @@ class DstSafetyAnalysis {
 
 // ... an address can be updated in a safe manner, or
 if (auto DstAndSrc = BC.MIB->analyzeAddressArithmeticsForPtrAuth(Inst)) {
-  MCPhysReg DstReg, SrcReg;
-  std::tie(DstReg, SrcReg) = *DstAndSrc;
+  auto [DstReg, SrcReg] = *DstAndSrc;
   // Note that *all* registers containing the derived values must be safe,
   // both source and destination ones. No temporaries are supported at now.
   if (Cur.CannotEscapeUnchecked[SrcReg] &&
@@ -1077,7 +1076,7 @@ class DstSafetyAnalysis {
 // If this instruction terminates the program immediately, no
 // authentication oracles are possible past this point.
 if (BC.MIB->isTrap(Point)) {
-  LLVM_DEBUG({ traceInst(BC, "Trap instruction found", Point); });
+  LLVM_DEBUG(traceInst(BC, "Trap instruction found", Point));
   DstState Next(NumRegs, RegsToTrackInstsFor.getNumTrackedRegisters());
   Next.CannotEscapeUnchecked.set();
   return Next;
@@ -1255,7 +1254,7 @@ class CFGUnawareDstSafetyAnalysis : public 
DstSafetyAnalysis,
   // starting to analyze Inst.
   

[llvm-branch-commits] [flang] [llvm] [openmp] [Flang] Add standalone tile support (PR #160298)

2025-09-24 Thread via llvm-branch-commits

llvmbot wrote:




@llvm/pr-subscribers-flang-fir-hlfir

Author: Michael Kruse (Meinersbur)


Changes

Add support for the standalone OpenMP tile construct:
```f90
!$omp tile sizes(...)
DO i = 1, 100
  ...
```

This is complementary to #143715 which added support for the tile 
construct as part of another loop-associated construct such as 
worksharing-loop, distribute, etc.

PR Stack:
 * #160283
 * #159773
 * #160292
 * #160298 (this PR)

---

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


25 Files Affected:

- (modified) flang/lib/Lower/OpenMP/ClauseProcessor.cpp (+13) 
- (modified) flang/lib/Lower/OpenMP/ClauseProcessor.h (+2) 
- (modified) flang/lib/Lower/OpenMP/OpenMP.cpp (+236-124) 
- (modified) flang/lib/Lower/OpenMP/Utils.cpp (+20-4) 
- (modified) flang/lib/Lower/OpenMP/Utils.h (+7) 
- (modified) flang/lib/Semantics/check-directive-structure.h (+4-3) 
- (modified) flang/lib/Semantics/check-omp-structure.cpp (+7-1) 
- (modified) flang/lib/Semantics/resolve-directives.cpp (+12-4) 
- (added) flang/test/Lower/OpenMP/tile01.f90 (+58) 
- (added) flang/test/Lower/OpenMP/tile02.f90 (+88) 
- (modified) flang/test/Parser/OpenMP/loop-transformation-construct02.f90 
(+3-2) 
- (added) flang/test/Parser/OpenMP/tile-fail.f90 (+32) 
- (modified) flang/test/Parser/OpenMP/tile.f90 (+10-5) 
- (added) flang/test/Semantics/OpenMP/tile01.f90 (+26) 
- (added) flang/test/Semantics/OpenMP/tile02.f90 (+15) 
- (added) flang/test/Semantics/OpenMP/tile03.f90 (+15) 
- (added) flang/test/Semantics/OpenMP/tile04.f90 (+38) 
- (added) flang/test/Semantics/OpenMP/tile05.f90 (+14) 
- (added) flang/test/Semantics/OpenMP/tile06.f90 (+44) 
- (added) flang/test/Semantics/OpenMP/tile07.f90 (+35) 
- (added) flang/test/Semantics/OpenMP/tile08.f90 (+15) 
- (modified) llvm/include/llvm/Frontend/OpenMP/OMP.td (+3) 
- (added) openmp/runtime/test/transform/tile/intfor.f90 (+31) 
- (added) openmp/runtime/test/transform/tile/intfor_2d.f90 (+53) 
- (added) openmp/runtime/test/transform/tile/intfor_2d_varsizes.F90 (+60) 


``diff
diff --git a/flang/lib/Lower/OpenMP/ClauseProcessor.cpp 
b/flang/lib/Lower/OpenMP/ClauseProcessor.cpp
index a96884f5680ba..55eda7e3404c1 100644
--- a/flang/lib/Lower/OpenMP/ClauseProcessor.cpp
+++ b/flang/lib/Lower/OpenMP/ClauseProcessor.cpp
@@ -431,6 +431,19 @@ bool ClauseProcessor::processNumTasks(
   return false;
 }
 
+bool ClauseProcessor::processSizes(StatementContext &stmtCtx,
+   mlir::omp::SizesClauseOps &result) const {
+  if (auto *clause = findUniqueClause()) {
+result.sizes.reserve(clause->v.size());
+for (const ExprTy &vv : clause->v)
+  result.sizes.push_back(fir::getBase(converter.genExprValue(vv, 
stmtCtx)));
+
+return true;
+  }
+
+  return false;
+}
+
 bool ClauseProcessor::processNumTeams(
 lower::StatementContext &stmtCtx,
 mlir::omp::NumTeamsClauseOps &result) const {
diff --git a/flang/lib/Lower/OpenMP/ClauseProcessor.h 
b/flang/lib/Lower/OpenMP/ClauseProcessor.h
index 324ea3c1047a5..9e352fa574a97 100644
--- a/flang/lib/Lower/OpenMP/ClauseProcessor.h
+++ b/flang/lib/Lower/OpenMP/ClauseProcessor.h
@@ -66,6 +66,8 @@ class ClauseProcessor {
   mlir::omp::LoopRelatedClauseOps &loopResult,
   mlir::omp::CollapseClauseOps &collapseResult,
   llvm::SmallVectorImpl &iv) const;
+  bool processSizes(StatementContext &stmtCtx,
+mlir::omp::SizesClauseOps &result) const;
   bool processDevice(lower::StatementContext &stmtCtx,
  mlir::omp::DeviceClauseOps &result) const;
   bool processDeviceType(mlir::omp::DeviceTypeClauseOps &result) const;
diff --git a/flang/lib/Lower/OpenMP/OpenMP.cpp 
b/flang/lib/Lower/OpenMP/OpenMP.cpp
index 5681be664d450..7812d9fe00be2 100644
--- a/flang/lib/Lower/OpenMP/OpenMP.cpp
+++ b/flang/lib/Lower/OpenMP/OpenMP.cpp
@@ -1984,125 +1984,241 @@ genLoopOp(lower::AbstractConverter &converter, 
lower::SymMap &symTable,
   return loopOp;
 }
 
-static mlir::omp::CanonicalLoopOp
-genCanonicalLoopOp(lower::AbstractConverter &converter, lower::SymMap 
&symTable,
-   semantics::SemanticsContext &semaCtx,
-   lower::pft::Evaluation &eval, mlir::Location loc,
-   const ConstructQueue &queue,
-   ConstructQueue::const_iterator item,
-   llvm::ArrayRef ivs,
-   llvm::omp::Directive directive) {
+static void genCanonicalLoopNest(
+lower::AbstractConverter &converter, lower::SymMap &symTable,
+semantics::SemanticsContext &semaCtx, lower::pft::Evaluation &eval,
+mlir::Location loc, const ConstructQueue &queue,
+ConstructQueue::const_iterator item, size_t numLoops,
+llvm::SmallVectorImpl &loops) {
+  assert(loops.empty() && "Expecting empty list to fill");
+  assert(numLoops >= 1 && "Expecting at least one loop");
+
   fir::FirOpBuilder &firOpBuilder = converter.getFirOp

[llvm-branch-commits] [flang] [llvm] [openmp] [Flang] Add standalone tile support (PR #160298)

2025-09-24 Thread Michael Kruse via llvm-branch-commits

https://github.com/Meinersbur ready_for_review 
https://github.com/llvm/llvm-project/pull/160298
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] [AllocToken, Clang] Implement __builtin_infer_alloc_token() and llvm.alloc.token.id (PR #156842)

2025-09-24 Thread Hans Wennborg via llvm-branch-commits

zmodem wrote:

> for `__builtin_infer_allocation_token` that won't work, because then we have 
> to pull out all the token calculation logic in a way that Clang can access 
> it. And some of that depends on configuration specific to the LLVM IR pass, 
> that is not yet known. Not sure if there's a clean way other than somehow 
> creating an API that can be used to do the token calculation that can be 
> shared between Clang and IR pass.

Separating the instrumentation pass and the token generation might be a good 
idea though? The pass could focus on IR manipulation, and there could be a 
separate utility for token generation.

I agree that it would make sense if this were constant evaluate-able since it 
is a compile time constant in the end, but I don't know whether there are 
actually important use cases for this.

https://github.com/llvm/llvm-project/pull/156842
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [LifetimeSafety] Introduce a liveness-based lifetime policy (PR #159991)

2025-09-24 Thread Utkarsh Saxena via llvm-branch-commits


@@ -1118,109 +1119,189 @@ class LoanPropagationAnalysis
 OriginLoanMapFactory.add(In.Origins, DestOID, MergedLoans));
   }
 
-  LoanSet getLoans(OriginID OID, ProgramPoint P) {
+  LoanSet getLoans(OriginID OID, ProgramPoint P) const {
 return getLoans(getState(P), OID);
   }
 
 private:
-  LoanSet getLoans(Lattice L, OriginID OID) {
+  LoanSet getLoans(Lattice L, OriginID OID) const {
 if (auto *Loans = L.Origins.lookup(OID))
   return *Loans;
 return LoanSetFactory.getEmptySet();
   }
 };
 
 // = //
-// Expired Loans Analysis
+// Live Origins Analysis
 // = //
 
-/// The dataflow lattice for tracking the set of expired loans.
-struct ExpiredLattice {
-  /// Map from an expired `LoanID` to the `ExpireFact` that made it expire.
-  ExpiredLoanMap Expired;
+/// Information about why an origin is live at a program point.
+struct LivenessInfo {
+  /// The use that makes the origin live. If liveness is propagated from
+  /// multiple uses along different paths, this will point to the use appearing
+  /// before in the translation unit.
+  const UseFact *CausingUseFact;
+  /// The confidence in the liveness of the origin.
+  /// `Definite`: The origin is live on all control-flow paths from the current
+  /// point to the function's exit (i.e. the current point is dominated by a 
set
+  /// of uses).
+  /// `Maybe`: indicates it is live on some but not all paths.
+  Confidence ConfidenceLevel;
+
+  LivenessInfo() : CausingUseFact(nullptr), ConfidenceLevel(Confidence::None) 
{}
+  LivenessInfo(const UseFact *UF, Confidence C)
+  : CausingUseFact(UF), ConfidenceLevel(C) {}
+
+  bool operator==(const LivenessInfo &Other) const {
+return CausingUseFact == Other.CausingUseFact &&
+   ConfidenceLevel == Other.ConfidenceLevel;
+  }
+  bool operator!=(const LivenessInfo &Other) const { return !(*this == Other); 
}
+
+  void Profile(llvm::FoldingSetNodeID &IDBuilder) const {
+IDBuilder.AddPointer(CausingUseFact);
+IDBuilder.Add(ConfidenceLevel);
+  }
+};
+
+using LivenessMap = llvm::ImmutableMap;
+
+/// The dataflow lattice for origin liveness analysis.
+/// It tracks which origins are live, why they're live (which UseFact),
+/// and the confidence level of that liveness.
+struct LivenessLattice {
+  LivenessMap LiveOrigins;
+
+  LivenessLattice() : LiveOrigins(nullptr) {};
 
-  ExpiredLattice() : Expired(nullptr) {};
-  explicit ExpiredLattice(ExpiredLoanMap M) : Expired(M) {}
+  explicit LivenessLattice(LivenessMap L) : LiveOrigins(L) {}
 
-  bool operator==(const ExpiredLattice &Other) const {
-return Expired == Other.Expired;
+  bool operator==(const LivenessLattice &Other) const {
+return LiveOrigins == Other.LiveOrigins;
   }
-  bool operator!=(const ExpiredLattice &Other) const {
+
+  bool operator!=(const LivenessLattice &Other) const {
 return !(*this == Other);
   }
 
-  void dump(llvm::raw_ostream &OS) const {
-OS << "ExpiredLattice State:\n";
-if (Expired.isEmpty())
+  void dump(llvm::raw_ostream &OS, const OriginManager &OM) const {
+if (LiveOrigins.isEmpty())
   OS << "  \n";
-for (const auto &[ID, _] : Expired)
-  OS << "  Loan " << ID << " is expired\n";
+for (const auto &Entry : LiveOrigins) {
+  OriginID OID = Entry.first;
+  const LivenessInfo &Info = Entry.second;
+  OS << "  ";
+  OM.dump(OID, OS);
+  OS << " is ";
+  switch (Info.ConfidenceLevel) {
+  case Confidence::Definite:
+OS << "definitely";
+break;
+  case Confidence::Maybe:
+OS << "maybe";
+break;
+  case Confidence::None:
+llvm_unreachable("liveness condidence should not be none.");
+  }
+  OS << " live at this point\n";
+}
   }
 };
 
-/// The analysis that tracks which loans have expired.
-class ExpiredLoansAnalysis
-: public DataflowAnalysis {
-
-  ExpiredLoanMap::Factory &Factory;
+/// The analysis that tracks which origins are live, with granular information
+/// about the causing use fact and confidence level. This is a backward
+/// analysis.
+class LiveOriginAnalysis
+: public DataflowAnalysis {
+  FactManager &FactMgr;
+  LivenessMap::Factory &Factory;
 
 public:
-  ExpiredLoansAnalysis(const CFG &C, AnalysisDeclContext &AC, FactManager &F,
-   LifetimeFactory &Factory)
-  : DataflowAnalysis(C, AC, F), Factory(Factory.ExpiredLoanMapFactory) {}
-
-  using Base::transfer;
+  LiveOriginAnalysis(const CFG &C, AnalysisDeclContext &AC, FactManager &F,
+ LivenessMap::Factory &SF)
+  : DataflowAnalysis(C, AC, F), FactMgr(F), Factory(SF) {}
+  using DataflowAnalysis::transfer;
 
-  StringRef getAnalysisName() const { return "ExpiredLoans"; }
+  StringRef getAnalysisName() const { return "LiveOrigins"; }
 
   

[llvm-branch-commits] [clang] [LifetimeSafety] Introduce a liveness-based lifetime policy (PR #159991)

2025-09-24 Thread Utkarsh Saxena via llvm-branch-commits


@@ -873,19 +874,26 @@ class DataflowAnalysis {
 llvm::SmallBitVector Visited(Cfg.getNumBlockIDs() + 1);
 
 while (const CFGBlock *B = W.dequeue()) {
-  Lattice StateIn = getInState(B);
+  Lattice StateIn = *getInState(B);
   Lattice StateOut = transferBlock(B, StateIn);
   OutStates[B] = StateOut;
-  Visited.set(B->getBlockID());
   for (const CFGBlock *AdjacentB : isForward() ? B->succs() : B->preds()) {
 if (!AdjacentB)
   continue;
-Lattice OldInState = getInState(AdjacentB);
-Lattice NewInState = D.join(OldInState, StateOut);
+Lattice OldInState;
+bool SawFirstTime = false;
+Lattice NewInState;
+if (const Lattice *In = getInState(AdjacentB)) {

usx95 wrote:

Reverted to original behaviour of `getInState` and used a separate bit vector 
to track visitations.

https://github.com/llvm/llvm-project/pull/159991
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [LifetimeSafety] Introduce a liveness-based lifetime policy (PR #159991)

2025-09-24 Thread Utkarsh Saxena via llvm-branch-commits

https://github.com/usx95 edited https://github.com/llvm/llvm-project/pull/159991
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] Greedy: Use initializer list for recoloring candidates (NFC) (PR #160486)

2025-09-24 Thread Luke Lau via llvm-branch-commits

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


https://github.com/llvm/llvm-project/pull/160486
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] Greedy: Use initializer list for recoloring candidates (NFC) (PR #160486)

2025-09-24 Thread Matt Arsenault via llvm-branch-commits

arsenm wrote:

> [!WARNING]
> This pull request is not mergeable via GitHub because a downstack PR is 
> open. Once all requirements are satisfied, merge this PR as a stack  href="https://app.graphite.dev/github/pr/llvm/llvm-project/160486?utm_source=stack-comment-downstack-mergeability-warning";
>  >on Graphite.
> https://graphite.dev/docs/merge-pull-requests";>Learn more

* **#160486** https://app.graphite.dev/github/pr/llvm/llvm-project/160486?utm_source=stack-comment-icon";
 target="_blank">https://static.graphite.dev/graphite-32x32-black.png"; alt="Graphite" 
width="10px" height="10px"/> 👈 https://app.graphite.dev/github/pr/llvm/llvm-project/160486?utm_source=stack-comment-view-in-graphite";
 target="_blank">(View in Graphite)
* **#160485** https://app.graphite.dev/github/pr/llvm/llvm-project/160485?utm_source=stack-comment-icon";
 target="_blank">https://static.graphite.dev/graphite-32x32-black.png"; alt="Graphite" 
width="10px" height="10px"/>
* **#160484** https://app.graphite.dev/github/pr/llvm/llvm-project/160484?utm_source=stack-comment-icon";
 target="_blank">https://static.graphite.dev/graphite-32x32-black.png"; alt="Graphite" 
width="10px" height="10px"/>
* **#160424** https://app.graphite.dev/github/pr/llvm/llvm-project/160424?utm_source=stack-comment-icon";
 target="_blank">https://static.graphite.dev/graphite-32x32-black.png"; alt="Graphite" 
width="10px" height="10px"/>: 1 other dependent PR 
([#160467](https://github.com/llvm/llvm-project/pull/160467) https://app.graphite.dev/github/pr/llvm/llvm-project/160467?utm_source=stack-comment-icon";
 target="_blank">https://static.graphite.dev/graphite-32x32-black.png"; alt="Graphite" 
width="10px" height="10px"/>)
* **#160294** https://app.graphite.dev/github/pr/llvm/llvm-project/160294?utm_source=stack-comment-icon";
 target="_blank">https://static.graphite.dev/graphite-32x32-black.png"; alt="Graphite" 
width="10px" height="10px"/>
* `main`




This stack of pull requests is managed by https://graphite.dev?utm-source=stack-comment";>Graphite. Learn 
more about https://stacking.dev/?utm_source=stack-comment";>stacking.


https://github.com/llvm/llvm-project/pull/160486
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] Greedy: Move physreg check when trying to recolor vregs (NFC) (PR #160484)

2025-09-24 Thread Luke Lau via llvm-branch-commits

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


https://github.com/llvm/llvm-project/pull/160484
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] Greedy: Use initializer list for recoloring candidates (NFC) (PR #160486)

2025-09-24 Thread Matt Arsenault via llvm-branch-commits

https://github.com/arsenm ready_for_review 
https://github.com/llvm/llvm-project/pull/160486
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] Greedy: Use initializer list for recoloring candidates (NFC) (PR #160486)

2025-09-24 Thread via llvm-branch-commits

llvmbot wrote:




@llvm/pr-subscribers-backend-x86

Author: Matt Arsenault (arsenm)


Changes



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


1 Files Affected:

- (modified) llvm/lib/CodeGen/RegAllocGreedy.cpp (+2-4) 


``diff
diff --git a/llvm/lib/CodeGen/RegAllocGreedy.cpp 
b/llvm/lib/CodeGen/RegAllocGreedy.cpp
index 6957548ac6c7a..bb8ebe7d7ddf1 100644
--- a/llvm/lib/CodeGen/RegAllocGreedy.cpp
+++ b/llvm/lib/CodeGen/RegAllocGreedy.cpp
@@ -2486,15 +2486,13 @@ void RAGreedy::tryHintRecoloring(const LiveInterval 
&VirtReg) {
   // We have a broken hint, check if it is possible to fix it by
   // reusing PhysReg for the copy-related live-ranges. Indeed, we evicted
   // some register and PhysReg may be available for the other live-ranges.
-  SmallSet Visited;
-  SmallVector RecoloringCandidates;
   HintsInfo Info;
   Register Reg = VirtReg.reg();
   MCRegister PhysReg = VRM->getPhys(Reg);
   // Start the recoloring algorithm from the input live-interval, then
   // it will propagate to the ones that are copy-related with it.
-  Visited.insert(Reg);
-  RecoloringCandidates.push_back(Reg);
+  SmallSet Visited = {Reg};
+  SmallVector RecoloringCandidates = {Reg};
 
   LLVM_DEBUG(dbgs() << "Trying to reconcile hints for: " << printReg(Reg, TRI)
 << '(' << printReg(PhysReg, TRI) << ")\n");

``




https://github.com/llvm/llvm-project/pull/160486
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] [BOLT] Gadget scanner: optionally assume auth traps on failure (PR #139778)

2025-09-24 Thread Anatoly Trosinenko via llvm-branch-commits

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

>From 8dc0489843c88abe4749f3e29775cea04050d925 Mon Sep 17 00:00:00 2001
From: Anatoly Trosinenko 
Date: Tue, 13 May 2025 19:50:41 +0300
Subject: [PATCH 1/2] [BOLT] Gadget scanner: optionally assume auth traps on
 failure

On AArch64 it is possible for an auth instruction to either return an
invalid address value on failure (without FEAT_FPAC) or generate an
error (with FEAT_FPAC). It thus may be possible to never emit explicit
pointer checks, if the target CPU is known to support FEAT_FPAC.

This commit implements an --auth-traps-on-failure command line option,
which essentially makes "safe-to-dereference" and "trusted" register
properties identical and disables scanning for authentication oracles
completely.
---
 bolt/lib/Passes/PAuthGadgetScanner.cpp| 112 +++
 .../binary-analysis/AArch64/cmdline-args.test |   1 +
 .../AArch64/gs-pauth-authentication-oracles.s |   6 +-
 .../binary-analysis/AArch64/gs-pauth-calls.s  |   5 +-
 .../AArch64/gs-pauth-debug-output.s   | 177 ++---
 .../AArch64/gs-pauth-jump-table.s |   6 +-
 .../AArch64/gs-pauth-signing-oracles.s|  54 ++---
 .../AArch64/gs-pauth-tail-calls.s | 184 +-
 8 files changed, 318 insertions(+), 227 deletions(-)

diff --git a/bolt/lib/Passes/PAuthGadgetScanner.cpp 
b/bolt/lib/Passes/PAuthGadgetScanner.cpp
index 3a6c3e3d925cf..4fc0bf2ae54a9 100644
--- a/bolt/lib/Passes/PAuthGadgetScanner.cpp
+++ b/bolt/lib/Passes/PAuthGadgetScanner.cpp
@@ -14,6 +14,7 @@
 #include "bolt/Passes/PAuthGadgetScanner.h"
 #include "bolt/Core/ParallelUtilities.h"
 #include "bolt/Passes/DataflowAnalysis.h"
+#include "bolt/Utils/CommandLineOpts.h"
 #include "llvm/ADT/STLExtras.h"
 #include "llvm/ADT/SmallSet.h"
 #include "llvm/MC/MCInst.h"
@@ -26,6 +27,11 @@ namespace llvm {
 namespace bolt {
 namespace PAuthGadgetScanner {
 
+static cl::opt AuthTrapsOnFailure(
+"auth-traps-on-failure",
+cl::desc("Assume authentication instructions always trap on failure"),
+cl::cat(opts::BinaryAnalysisCategory));
+
 [[maybe_unused]] static void traceInst(const BinaryContext &BC, StringRef 
Label,
const MCInst &MI) {
   dbgs() << "  " << Label << ": ";
@@ -364,6 +370,34 @@ class SrcSafetyAnalysis {
 return Clobbered;
   }
 
+  std::optional getRegMadeTrustedByChecking(const MCInst &Inst,
+   SrcState Cur) const {
+// This functions cannot return multiple registers. This is never the case
+// on AArch64.
+std::optional RegCheckedByInst =
+BC.MIB->getAuthCheckedReg(Inst, /*MayOverwrite=*/false);
+if (RegCheckedByInst && Cur.SafeToDerefRegs[*RegCheckedByInst])
+  return *RegCheckedByInst;
+
+auto It = CheckerSequenceInfo.find(&Inst);
+if (It == CheckerSequenceInfo.end())
+  return std::nullopt;
+
+MCPhysReg RegCheckedBySequence = It->second.first;
+const MCInst *FirstCheckerInst = It->second.second;
+
+// FirstCheckerInst should belong to the same basic block (see the
+// assertion in DataflowSrcSafetyAnalysis::run()), meaning it was
+// deterministically processed a few steps before this instruction.
+const SrcState &StateBeforeChecker = getStateBefore(*FirstCheckerInst);
+
+// The sequence checks the register, but it should be authenticated before.
+if (!StateBeforeChecker.SafeToDerefRegs[RegCheckedBySequence])
+  return std::nullopt;
+
+return RegCheckedBySequence;
+  }
+
   // Returns all registers that can be treated as if they are written by an
   // authentication instruction.
   SmallVector getRegsMadeSafeToDeref(const MCInst &Point,
@@ -386,18 +420,38 @@ class SrcSafetyAnalysis {
 Regs.push_back(DstAndSrc->first);
 }
 
+// Make sure explicit checker sequence keeps register safe-to-dereference
+// when the register would be clobbered according to the regular rules:
+//
+//; LR is safe to dereference here
+//mov   x16, x30  ; start of the sequence, LR is s-t-d right before
+//xpaclri ; clobbers LR, LR is not safe anymore
+//cmp   x30, x16
+//b.eq  1f; end of the sequence: LR is marked as trusted
+//brk   0x1234
+//  1:
+//; at this point LR would be marked as trusted,
+//; but not safe-to-dereference
+//
+// or even just
+//
+//; X1 is safe to dereference here
+//ldr x0, [x1, #8]!
+//; X1 is trusted here, but it was clobbered due to address write-back
+if (auto CheckedReg = getRegMadeTrustedByChecking(Point, Cur))
+  Regs.push_back(*CheckedReg);
+
 return Regs;
   }
 
   // Returns all registers made trusted by this instruction.
   SmallVector getRegsMadeTrusted(const MCInst &Point,
 const SrcState &Cur) const {
+assert(!AuthTrapsOnFailur

[llvm-branch-commits] [llvm] [BOLT] Gadget scanner: prevent false positives due to jump tables (PR #138884)

2025-09-24 Thread Anatoly Trosinenko via llvm-branch-commits

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

>From 5c1edeb727636b1dcbf6573dd4d3f9d14abd8799 Mon Sep 17 00:00:00 2001
From: Anatoly Trosinenko 
Date: Tue, 6 May 2025 11:31:03 +0300
Subject: [PATCH] [BOLT] Gadget scanner: prevent false positives due to jump
 tables

As part of PAuth hardening, AArch64 LLVM backend can use a special
BR_JumpTable pseudo (enabled by -faarch64-jump-table-hardening
Clang option) which is expanded in the AsmPrinter into a contiguous
sequence without unsafe instructions in the middle.

This commit adds another target-specific callback to MCPlusBuilder
to make it possible to inhibit false positives for known-safe jump
table dispatch sequences. Without special handling, the branch
instruction is likely to be reported as a non-protected call (as its
destination is not produced by an auth instruction, PC-relative address
materialization, etc.) and possibly as a tail call being performed with
unsafe link register (as the detection whether the branch instruction
is a tail call is an heuristic).

For now, only the specific instruction sequence used by the AArch64
LLVM backend is matched.
---
 bolt/include/bolt/Core/MCInstUtils.h  |   9 +
 bolt/include/bolt/Core/MCPlusBuilder.h|  14 +
 bolt/lib/Core/MCInstUtils.cpp |  20 +
 bolt/lib/Passes/PAuthGadgetScanner.cpp|  10 +
 .../Target/AArch64/AArch64MCPlusBuilder.cpp   |  73 ++
 .../AArch64/gs-pauth-jump-table.s | 703 ++
 6 files changed, 829 insertions(+)
 create mode 100644 bolt/test/binary-analysis/AArch64/gs-pauth-jump-table.s

diff --git a/bolt/include/bolt/Core/MCInstUtils.h 
b/bolt/include/bolt/Core/MCInstUtils.h
index 2436e1359f40e..2df2054712457 100644
--- a/bolt/include/bolt/Core/MCInstUtils.h
+++ b/bolt/include/bolt/Core/MCInstUtils.h
@@ -142,6 +142,15 @@ class MCInstReference {
 return nullptr;
   }
 
+  /// Returns the only preceding instruction, or std::nullopt if multiple or no
+  /// predecessors are possible.
+  ///
+  /// If CFG information is available, basic block boundary can be crossed,
+  /// provided there is exactly one predecessor. If CFG is not available, the
+  /// preceding instruction in the offset order is returned, unless this is the
+  /// first instruction of the function.
+  std::optional getSinglePredecessor();
+
   raw_ostream &print(raw_ostream &OS) const;
 };
 
diff --git a/bolt/include/bolt/Core/MCPlusBuilder.h 
b/bolt/include/bolt/Core/MCPlusBuilder.h
index ae04891e791f9..f13e41c75c2ac 100644
--- a/bolt/include/bolt/Core/MCPlusBuilder.h
+++ b/bolt/include/bolt/Core/MCPlusBuilder.h
@@ -14,6 +14,7 @@
 #ifndef BOLT_CORE_MCPLUSBUILDER_H
 #define BOLT_CORE_MCPLUSBUILDER_H
 
+#include "bolt/Core/MCInstUtils.h"
 #include "bolt/Core/MCPlus.h"
 #include "bolt/Core/Relocation.h"
 #include "llvm/ADT/ArrayRef.h"
@@ -711,6 +712,19 @@ class MCPlusBuilder {
 return std::nullopt;
   }
 
+  /// Tests if BranchInst corresponds to an instruction sequence which is known
+  /// to be a safe dispatch via jump table.
+  ///
+  /// The target can decide which instruction sequences to consider "safe" from
+  /// the Pointer Authentication point of view, such as any jump table dispatch
+  /// sequence without function calls inside, any sequence which is contiguous,
+  /// or only some specific well-known sequences.
+  virtual bool
+  isSafeJumpTableBranchForPtrAuth(MCInstReference BranchInst) const {
+llvm_unreachable("not implemented");
+return false;
+  }
+
   virtual bool isTerminator(const MCInst &Inst) const;
 
   virtual bool isNoop(const MCInst &Inst) const {
diff --git a/bolt/lib/Core/MCInstUtils.cpp b/bolt/lib/Core/MCInstUtils.cpp
index 3cdb9673d4dc0..39bc96f087f8e 100644
--- a/bolt/lib/Core/MCInstUtils.cpp
+++ b/bolt/lib/Core/MCInstUtils.cpp
@@ -54,3 +54,23 @@ raw_ostream &MCInstReference::print(raw_ostream &OS) const {
   OS << ">";
   return OS;
 }
+
+std::optional MCInstReference::getSinglePredecessor() {
+  if (const RefInBB *Ref = tryGetRefInBB()) {
+if (Ref->It != Ref->BB->begin())
+  return MCInstReference(Ref->BB, &*std::prev(Ref->It));
+
+if (Ref->BB->pred_size() != 1)
+  return std::nullopt;
+
+BinaryBasicBlock *PredBB = *Ref->BB->pred_begin();
+assert(!PredBB->empty() && "Empty basic blocks are not supported yet");
+return MCInstReference(PredBB, &*PredBB->rbegin());
+  }
+
+  const RefInBF &Ref = getRefInBF();
+  if (Ref.It == Ref.BF->instrs().begin())
+return std::nullopt;
+
+  return MCInstReference(Ref.BF, std::prev(Ref.It));
+}
diff --git a/bolt/lib/Passes/PAuthGadgetScanner.cpp 
b/bolt/lib/Passes/PAuthGadgetScanner.cpp
index 5d884e2d37354..3a6c3e3d925cf 100644
--- a/bolt/lib/Passes/PAuthGadgetScanner.cpp
+++ b/bolt/lib/Passes/PAuthGadgetScanner.cpp
@@ -1370,6 +1370,11 @@ shouldReportUnsafeTailCall(const BinaryContext &BC, 
const BinaryFunction &BF,
 return std::nullopt;
   }
 
+  if (BC.MIB->isSafeJumpTableBranchForPtrAuth(Inst)) {
+LL

[llvm-branch-commits] [llvm] [BOLT] Gadget scanner: make use of C++17 features and LLVM helpers (PR #141665)

2025-09-24 Thread Anatoly Trosinenko via llvm-branch-commits

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

>From 9e5d66ac23bd52eb56f959812426e4acaaa58a19 Mon Sep 17 00:00:00 2001
From: Anatoly Trosinenko 
Date: Tue, 27 May 2025 21:06:03 +0300
Subject: [PATCH] [BOLT] Gadget scanner: make use of C++17 features and LLVM
 helpers

Perform trivial syntactical cleanups:
* make use of structured binding declarations
* use LLVM utility functions when appropriate
* omit braces around single expression inside single-line LLVM_DEBUG()

This patch is NFC aside from minor debug output changes.
---
 bolt/lib/Passes/PAuthGadgetScanner.cpp| 67 +--
 .../AArch64/gs-pauth-debug-output.s   | 14 ++--
 2 files changed, 38 insertions(+), 43 deletions(-)

diff --git a/bolt/lib/Passes/PAuthGadgetScanner.cpp 
b/bolt/lib/Passes/PAuthGadgetScanner.cpp
index 192b1da27759e..cfc0bc2cfc0da 100644
--- a/bolt/lib/Passes/PAuthGadgetScanner.cpp
+++ b/bolt/lib/Passes/PAuthGadgetScanner.cpp
@@ -88,8 +88,8 @@ class TrackedRegisters {
   TrackedRegisters(ArrayRef RegsToTrack)
   : Registers(RegsToTrack),
 RegToIndexMapping(getMappingSize(RegsToTrack), NoIndex) {
-for (unsigned I = 0; I < RegsToTrack.size(); ++I)
-  RegToIndexMapping[RegsToTrack[I]] = I;
+for (auto [MappedIndex, Reg] : llvm::enumerate(RegsToTrack))
+  RegToIndexMapping[Reg] = MappedIndex;
   }
 
   ArrayRef getRegisters() const { return Registers; }
@@ -203,9 +203,9 @@ struct SrcState {
 
 SafeToDerefRegs &= StateIn.SafeToDerefRegs;
 TrustedRegs &= StateIn.TrustedRegs;
-for (unsigned I = 0; I < LastInstWritingReg.size(); ++I)
-  for (const MCInst *J : StateIn.LastInstWritingReg[I])
-LastInstWritingReg[I].insert(J);
+for (auto [ThisSet, OtherSet] :
+ llvm::zip_equal(LastInstWritingReg, StateIn.LastInstWritingReg))
+  ThisSet.insert_range(OtherSet);
 return *this;
   }
 
@@ -224,11 +224,9 @@ struct SrcState {
 static void printInstsShort(raw_ostream &OS,
 ArrayRef Insts) {
   OS << "Insts: ";
-  for (unsigned I = 0; I < Insts.size(); ++I) {
-auto &Set = Insts[I];
+  for (auto [I, PtrSet] : llvm::enumerate(Insts)) {
 OS << "[" << I << "](";
-for (const MCInst *MCInstP : Set)
-  OS << MCInstP << " ";
+interleave(PtrSet, OS, " ");
 OS << ")";
   }
 }
@@ -416,8 +414,9 @@ class SrcSafetyAnalysis {
 // ... an address can be updated in a safe manner, producing the result
 // which is as trusted as the input address.
 if (auto DstAndSrc = BC.MIB->analyzeAddressArithmeticsForPtrAuth(Point)) {
-  if (Cur.SafeToDerefRegs[DstAndSrc->second])
-Regs.push_back(DstAndSrc->first);
+  auto [DstReg, SrcReg] = *DstAndSrc;
+  if (Cur.SafeToDerefRegs[SrcReg])
+Regs.push_back(DstReg);
 }
 
 // Make sure explicit checker sequence keeps register safe-to-dereference
@@ -469,8 +468,9 @@ class SrcSafetyAnalysis {
 // ... an address can be updated in a safe manner, producing the result
 // which is as trusted as the input address.
 if (auto DstAndSrc = BC.MIB->analyzeAddressArithmeticsForPtrAuth(Point)) {
-  if (Cur.TrustedRegs[DstAndSrc->second])
-Regs.push_back(DstAndSrc->first);
+  auto [DstReg, SrcReg] = *DstAndSrc;
+  if (Cur.TrustedRegs[SrcReg])
+Regs.push_back(DstReg);
 }
 
 return Regs;
@@ -868,9 +868,9 @@ struct DstState {
   return (*this = StateIn);
 
 CannotEscapeUnchecked &= StateIn.CannotEscapeUnchecked;
-for (unsigned I = 0; I < FirstInstLeakingReg.size(); ++I)
-  for (const MCInst *J : StateIn.FirstInstLeakingReg[I])
-FirstInstLeakingReg[I].insert(J);
+for (auto [ThisSet, OtherSet] :
+ llvm::zip_equal(FirstInstLeakingReg, StateIn.FirstInstLeakingReg))
+  ThisSet.insert_range(OtherSet);
 return *this;
   }
 
@@ -1036,8 +1036,7 @@ class DstSafetyAnalysis {
 
 // ... an address can be updated in a safe manner, or
 if (auto DstAndSrc = BC.MIB->analyzeAddressArithmeticsForPtrAuth(Inst)) {
-  MCPhysReg DstReg, SrcReg;
-  std::tie(DstReg, SrcReg) = *DstAndSrc;
+  auto [DstReg, SrcReg] = *DstAndSrc;
   // Note that *all* registers containing the derived values must be safe,
   // both source and destination ones. No temporaries are supported at now.
   if (Cur.CannotEscapeUnchecked[SrcReg] &&
@@ -1077,7 +1076,7 @@ class DstSafetyAnalysis {
 // If this instruction terminates the program immediately, no
 // authentication oracles are possible past this point.
 if (BC.MIB->isTrap(Point)) {
-  LLVM_DEBUG({ traceInst(BC, "Trap instruction found", Point); });
+  LLVM_DEBUG(traceInst(BC, "Trap instruction found", Point));
   DstState Next(NumRegs, RegsToTrackInstsFor.getNumTrackedRegisters());
   Next.CannotEscapeUnchecked.set();
   return Next;
@@ -1255,7 +1254,7 @@ class CFGUnawareDstSafetyAnalysis : public 
DstSafetyAnalysis,
   // starting to analyze Inst.
   

[llvm-branch-commits] [clang] [LifetimeSafety] Introduce a liveness-based lifetime policy (PR #159991)

2025-09-24 Thread Gábor Horváth via llvm-branch-commits


@@ -1118,109 +1119,189 @@ class LoanPropagationAnalysis
 OriginLoanMapFactory.add(In.Origins, DestOID, MergedLoans));
   }
 
-  LoanSet getLoans(OriginID OID, ProgramPoint P) {
+  LoanSet getLoans(OriginID OID, ProgramPoint P) const {
 return getLoans(getState(P), OID);
   }
 
 private:
-  LoanSet getLoans(Lattice L, OriginID OID) {
+  LoanSet getLoans(Lattice L, OriginID OID) const {
 if (auto *Loans = L.Origins.lookup(OID))
   return *Loans;
 return LoanSetFactory.getEmptySet();
   }
 };
 
 // = //
-// Expired Loans Analysis
+// Live Origins Analysis
 // = //
 
-/// The dataflow lattice for tracking the set of expired loans.
-struct ExpiredLattice {
-  /// Map from an expired `LoanID` to the `ExpireFact` that made it expire.
-  ExpiredLoanMap Expired;
+/// Information about why an origin is live at a program point.
+struct LivenessInfo {
+  /// The use that makes the origin live. If liveness is propagated from
+  /// multiple uses along different paths, this will point to the use appearing
+  /// before in the translation unit.
+  const UseFact *CausingUseFact;
+  /// The confidence in the liveness of the origin.
+  /// `Definite`: The origin is live on all control-flow paths from the current
+  /// point to the function's exit (i.e. the current point is dominated by a 
set
+  /// of uses).
+  /// `Maybe`: indicates it is live on some but not all paths.
+  Confidence ConfidenceLevel;
+
+  LivenessInfo() : CausingUseFact(nullptr), ConfidenceLevel(Confidence::None) 
{}
+  LivenessInfo(const UseFact *UF, Confidence C)
+  : CausingUseFact(UF), ConfidenceLevel(C) {}
+
+  bool operator==(const LivenessInfo &Other) const {
+return CausingUseFact == Other.CausingUseFact &&
+   ConfidenceLevel == Other.ConfidenceLevel;
+  }
+  bool operator!=(const LivenessInfo &Other) const { return !(*this == Other); 
}
+
+  void Profile(llvm::FoldingSetNodeID &IDBuilder) const {
+IDBuilder.AddPointer(CausingUseFact);
+IDBuilder.Add(ConfidenceLevel);
+  }
+};
+
+using LivenessMap = llvm::ImmutableMap;
+
+/// The dataflow lattice for origin liveness analysis.
+/// It tracks which origins are live, why they're live (which UseFact),
+/// and the confidence level of that liveness.
+struct LivenessLattice {
+  LivenessMap LiveOrigins;
+
+  LivenessLattice() : LiveOrigins(nullptr) {};
 
-  ExpiredLattice() : Expired(nullptr) {};
-  explicit ExpiredLattice(ExpiredLoanMap M) : Expired(M) {}
+  explicit LivenessLattice(LivenessMap L) : LiveOrigins(L) {}
 
-  bool operator==(const ExpiredLattice &Other) const {
-return Expired == Other.Expired;
+  bool operator==(const LivenessLattice &Other) const {
+return LiveOrigins == Other.LiveOrigins;
   }
-  bool operator!=(const ExpiredLattice &Other) const {
+
+  bool operator!=(const LivenessLattice &Other) const {
 return !(*this == Other);
   }
 
-  void dump(llvm::raw_ostream &OS) const {
-OS << "ExpiredLattice State:\n";
-if (Expired.isEmpty())
+  void dump(llvm::raw_ostream &OS, const OriginManager &OM) const {
+if (LiveOrigins.isEmpty())
   OS << "  \n";
-for (const auto &[ID, _] : Expired)
-  OS << "  Loan " << ID << " is expired\n";
+for (const auto &Entry : LiveOrigins) {
+  OriginID OID = Entry.first;
+  const LivenessInfo &Info = Entry.second;
+  OS << "  ";
+  OM.dump(OID, OS);
+  OS << " is ";
+  switch (Info.ConfidenceLevel) {
+  case Confidence::Definite:
+OS << "definitely";
+break;
+  case Confidence::Maybe:
+OS << "maybe";
+break;
+  case Confidence::None:
+llvm_unreachable("liveness condidence should not be none.");
+  }
+  OS << " live at this point\n";
+}
   }
 };
 
-/// The analysis that tracks which loans have expired.
-class ExpiredLoansAnalysis
-: public DataflowAnalysis {
-
-  ExpiredLoanMap::Factory &Factory;
+/// The analysis that tracks which origins are live, with granular information
+/// about the causing use fact and confidence level. This is a backward
+/// analysis.
+class LiveOriginAnalysis
+: public DataflowAnalysis {
+  FactManager &FactMgr;
+  LivenessMap::Factory &Factory;
 
 public:
-  ExpiredLoansAnalysis(const CFG &C, AnalysisDeclContext &AC, FactManager &F,
-   LifetimeFactory &Factory)
-  : DataflowAnalysis(C, AC, F), Factory(Factory.ExpiredLoanMapFactory) {}
-
-  using Base::transfer;
+  LiveOriginAnalysis(const CFG &C, AnalysisDeclContext &AC, FactManager &F,
+ LivenessMap::Factory &SF)
+  : DataflowAnalysis(C, AC, F), FactMgr(F), Factory(SF) {}
+  using DataflowAnalysis::transfer;
 
-  StringRef getAnalysisName() const { return "ExpiredLoans"; }
+  StringRef getAnalysisName() const { return "LiveOrigins"; }
 
   

[llvm-branch-commits] [clang] [LifetimeSafety] Introduce a liveness-based lifetime policy (PR #159991)

2025-09-24 Thread Gábor Horváth via llvm-branch-commits


@@ -873,19 +874,26 @@ class DataflowAnalysis {
 llvm::SmallBitVector Visited(Cfg.getNumBlockIDs() + 1);
 
 while (const CFGBlock *B = W.dequeue()) {
-  Lattice StateIn = getInState(B);
+  Lattice StateIn = *getInState(B);
   Lattice StateOut = transferBlock(B, StateIn);
   OutStates[B] = StateOut;
-  Visited.set(B->getBlockID());
   for (const CFGBlock *AdjacentB : isForward() ? B->succs() : B->preds()) {
 if (!AdjacentB)
   continue;
-Lattice OldInState = getInState(AdjacentB);
-Lattice NewInState = D.join(OldInState, StateOut);
+Lattice OldInState;
+bool SawFirstTime = false;
+Lattice NewInState;
+if (const Lattice *In = getInState(AdjacentB)) {

Xazax-hun wrote:

Wouldn't it be simpler if `getInState` always returned a valid state? Just 
defaulted to `D.getInitialState` when the lookup fail. 

https://github.com/llvm/llvm-project/pull/159991
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [LifetimeSafety] Introduce a liveness-based lifetime policy (PR #159991)

2025-09-24 Thread Gábor Horváth via llvm-branch-commits


@@ -1085,11 +1080,17 @@ class LoanPropagationAnalysis
   /// Merges two lattices by taking the union of loans for each origin.
   // TODO(opt): Keep the state small by removing origins which become dead.
   Lattice join(Lattice A, Lattice B) {
-OriginLoanMap JoinedOrigins =
-utils::join(A.Origins, B.Origins, OriginLoanMapFactory,
-[&](LoanSet S1, LoanSet S2) {
-  return utils::join(S1, S2, LoanSetFactory);
-});
+OriginLoanMap JoinedOrigins = utils::join(
+A.Origins, B.Origins, OriginLoanMapFactory,
+[&](const LoanSet *S1, const LoanSet *S2) {
+  assert((S1 || S2) && "unexpectedly merging 2 empty sets");
+  if (!S1)
+return *S2;
+  if (!S2)
+return *S1;
+  return utils::join(*S1, *S2, LoanSetFactory);
+},
+/*JoinAllKeys=*/false);

Xazax-hun wrote:

Could you elaborate on why do we not want to join all the keys?

https://github.com/llvm/llvm-project/pull/159991
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] [LoongArch] Override cost hooks to expose more DAG combine opportunities (PR #157824)

2025-09-24 Thread via llvm-branch-commits

https://github.com/zhaoqi5 edited 
https://github.com/llvm/llvm-project/pull/157824
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] Greedy: Merge VirtRegMap queries into one use (NFC) (PR #160485)

2025-09-24 Thread Matt Arsenault via llvm-branch-commits

https://github.com/arsenm created 
https://github.com/llvm/llvm-project/pull/160485

None

>From 549ba6c5469304a2949e2a1482f2a18a42ee1d54 Mon Sep 17 00:00:00 2001
From: Matt Arsenault 
Date: Wed, 24 Sep 2025 19:06:39 +0900
Subject: [PATCH] Greedy: Merge VirtRegMap queries into one use (NFC)

---
 llvm/lib/CodeGen/RegAllocGreedy.cpp | 5 +++--
 1 file changed, 3 insertions(+), 2 deletions(-)

diff --git a/llvm/lib/CodeGen/RegAllocGreedy.cpp 
b/llvm/lib/CodeGen/RegAllocGreedy.cpp
index dc23ab3ce9d2b..6957548ac6c7a 100644
--- a/llvm/lib/CodeGen/RegAllocGreedy.cpp
+++ b/llvm/lib/CodeGen/RegAllocGreedy.cpp
@@ -2502,8 +2502,10 @@ void RAGreedy::tryHintRecoloring(const LiveInterval 
&VirtReg) {
   do {
 Reg = RecoloringCandidates.pop_back_val();
 
+MCRegister CurrPhys = VRM->getPhys(Reg);
+
 // This may be a skipped register.
-if (!VRM->hasPhys(Reg)) {
+if (!CurrPhys) {
   assert(!shouldAllocateRegister(Reg) &&
  "We have an unallocated variable which should have been handled");
   continue;
@@ -2512,7 +2514,6 @@ void RAGreedy::tryHintRecoloring(const LiveInterval 
&VirtReg) {
 // Get the live interval mapped with this virtual register to be able
 // to check for the interference with the new color.
 LiveInterval &LI = LIS->getInterval(Reg);
-MCRegister CurrPhys = VRM->getPhys(Reg);
 // Check that the new color matches the register class constraints and
 // that it is free for this live range.
 if (CurrPhys != PhysReg && (!MRI->getRegClass(Reg)->contains(PhysReg) ||

___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] Greedy: Move physreg check when trying to recolor vregs (NFC) (PR #160484)

2025-09-24 Thread via llvm-branch-commits

llvmbot wrote:




@llvm/pr-subscribers-backend-systemz

Author: Matt Arsenault (arsenm)


Changes

Instead of checking if the recoloring candidate is a virtual register,
avoid adding it to the candidates in the first place.

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


1 Files Affected:

- (modified) llvm/lib/CodeGen/RegAllocGreedy.cpp (+2-5) 


``diff
diff --git a/llvm/lib/CodeGen/RegAllocGreedy.cpp 
b/llvm/lib/CodeGen/RegAllocGreedy.cpp
index 6e0585b2e9e55..dc23ab3ce9d2b 100644
--- a/llvm/lib/CodeGen/RegAllocGreedy.cpp
+++ b/llvm/lib/CodeGen/RegAllocGreedy.cpp
@@ -2502,10 +2502,6 @@ void RAGreedy::tryHintRecoloring(const LiveInterval 
&VirtReg) {
   do {
 Reg = RecoloringCandidates.pop_back_val();
 
-// We cannot recolor physical register.
-if (Reg.isPhysical())
-  continue;
-
 // This may be a skipped register.
 if (!VRM->hasPhys(Reg)) {
   assert(!shouldAllocateRegister(Reg) &&
@@ -2553,7 +2549,8 @@ void RAGreedy::tryHintRecoloring(const LiveInterval 
&VirtReg) {
 // Push all copy-related live-ranges to keep reconciling the broken
 // hints.
 for (const HintInfo &HI : Info) {
-  if (Visited.insert(HI.Reg).second)
+  // We cannot recolor physical register.
+  if (HI.Reg.isVirtual() && Visited.insert(HI.Reg).second)
 RecoloringCandidates.push_back(HI.Reg);
 }
   } while (!RecoloringCandidates.empty());

``




https://github.com/llvm/llvm-project/pull/160484
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] Greedy: Merge VirtRegMap queries into one use (NFC) (PR #160485)

2025-09-24 Thread Matt Arsenault via llvm-branch-commits

https://github.com/arsenm ready_for_review 
https://github.com/llvm/llvm-project/pull/160485
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [llvm] [DirectX] Updating Root Signature Metadata to contain Static Sampler flags (PR #160210)

2025-09-24 Thread via llvm-branch-commits

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

>From 6b191d041990ad667d86b6b07eeed7c802e3fe45 Mon Sep 17 00:00:00 2001
From: Joao Saffran 
Date: Mon, 22 Sep 2025 15:31:47 -0700
Subject: [PATCH 1/2] adding metadata static sampler flags

---
 clang/test/CodeGenHLSL/RootSignature.hlsl |  4 +-
 .../Frontend/HLSL/RootSignatureMetadata.cpp   | 14 +-
 ...gnature-StaticSamplers-Invalid-AddressU.ll |  2 +-
 ...gnature-StaticSamplers-Invalid-AddressV.ll |  2 +-
 ...gnature-StaticSamplers-Invalid-AddressW.ll |  2 +-
 ...ture-StaticSamplers-Invalid-BorderColor.ll |  2 +-
 ...e-StaticSamplers-Invalid-ComparisonFunc.ll |  2 +-
 ...Signature-StaticSamplers-Invalid-Filter.ll |  2 +-
 ...re-StaticSamplers-Invalid-MaxAnisotropy.ll |  2 +-
 ...Signature-StaticSamplers-Invalid-MaxLod.ll |  2 +-
 ...Signature-StaticSamplers-Invalid-MinLod.ll |  2 +-
 ...ature-StaticSamplers-Invalid-MinLopBias.ll |  2 +-
 ...re-StaticSamplers-Invalid-RegisterSpace.ll |  2 +-
 ...e-StaticSamplers-Invalid-ShaderRegister.ll |  2 +-
 ...StaticSamplers-Invalid-ShaderVisibility.ll |  2 +-
 .../RootSignature-StaticSamplers.ll   |  2 +-
 .../RootSignature-StaticSamplers_V3.ll| 43 +++
 .../rootsignature-validation-fail-sampler.ll  |  2 +-
 ...re-validation-fail-static-sampler-range.ll |  4 +-
 19 files changed, 75 insertions(+), 20 deletions(-)
 create mode 100644 
llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers_V3.ll

diff --git a/clang/test/CodeGenHLSL/RootSignature.hlsl 
b/clang/test/CodeGenHLSL/RootSignature.hlsl
index bc40bdd79ce59..bbab6a73a3658 100644
--- a/clang/test/CodeGenHLSL/RootSignature.hlsl
+++ b/clang/test/CodeGenHLSL/RootSignature.hlsl
@@ -82,8 +82,8 @@ void RootDescriptorsEntry() {}
 // checking minLOD, maxLOD
 // CHECK-SAME: float -1.28e+02, float 1.28e+02,
 
-// checking register, space and visibility
-// CHECK-SAME: i32 42, i32 0, i32 0}
+// checking register, space, visibility and flags
+// CHECK-SAME: i32 42, i32 0, i32 0, i32 0}
 
 #define SampleStaticSampler \
   "StaticSampler(s42, " \
diff --git a/llvm/lib/Frontend/HLSL/RootSignatureMetadata.cpp 
b/llvm/lib/Frontend/HLSL/RootSignatureMetadata.cpp
index f29f2c7602fc6..5ddf129265648 100644
--- a/llvm/lib/Frontend/HLSL/RootSignatureMetadata.cpp
+++ b/llvm/lib/Frontend/HLSL/RootSignatureMetadata.cpp
@@ -212,6 +212,7 @@ MDNode *MetadataBuilder::BuildStaticSampler(const 
StaticSampler &Sampler) {
   ConstantAsMetadata::get(Builder.getInt32(Sampler.Space)),
   ConstantAsMetadata::get(
   Builder.getInt32(to_underlying(Sampler.Visibility))),
+  ConstantAsMetadata::get(Builder.getInt32(0)),
   };
   return MDNode::get(Ctx, Operands);
 }
@@ -411,7 +412,7 @@ Error 
MetadataParser::parseDescriptorTable(mcdxbc::RootSignatureDesc &RSD,
 
 Error MetadataParser::parseStaticSampler(mcdxbc::RootSignatureDesc &RSD,
  MDNode *StaticSamplerNode) {
-  if (StaticSamplerNode->getNumOperands() != 14)
+  if (StaticSamplerNode->getNumOperands() != 15)
 return make_error("Static Sampler");
 
   mcdxbc::StaticSampler Sampler;
@@ -495,6 +496,17 @@ Error 
MetadataParser::parseStaticSampler(mcdxbc::RootSignatureDesc &RSD,
 return Error(std::move(E));
   Sampler.ShaderVisibility = *Visibility;
 
+  if (RSD.Version < 3) {
+RSD.StaticSamplers.push_back(Sampler);
+return Error::success();
+  }
+  assert(RSD.Version >= 3);
+
+  if (std::optional Val = extractMdIntValue(StaticSamplerNode, 14))
+Sampler.Flags = *Val;
+  else
+return make_error("Static Sampler Flags");
+
   RSD.StaticSamplers.push_back(Sampler);
   return Error::success();
 }
diff --git 
a/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers-Invalid-AddressU.ll
 
b/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers-Invalid-AddressU.ll
index 288dea00b6e55..b043ea1418df6 100644
--- 
a/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers-Invalid-AddressU.ll
+++ 
b/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers-Invalid-AddressU.ll
@@ -16,4 +16,4 @@ 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 = !{ !"StaticSampler", i32 4, i32 666, i32 3, i32 5, float 
0x3FF6C000, i32 9, i32 3, i32 2, float -1.28e+02, float 
1.28e+02, i32 42, i32 0, i32 0 }
+!5 = !{ !"StaticSampler", i32 4, i32 666, i32 3, i32 5, float 
0x3FF6C000, i32 9, i32 3, i32 2, float -1.28e+02, float 
1.28e+02, i32 42, i32 0, i32 0, i32 0 }
diff --git 
a/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers-Invalid-AddressV.ll
 
b/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers-Invalid-AddressV.ll
index e9abcf966..8219ffdd679d2 100644
--- 
a/llvm/test/CodeGen/D

[llvm-branch-commits] [llvm] [profcheck][SimplifyCFG] Propagate !prof from `switch` to `select` (PR #159645)

2025-09-24 Thread Mircea Trofin via llvm-branch-commits

https://github.com/mtrofin updated 
https://github.com/llvm/llvm-project/pull/159645

>From 8027f039bd2b99e46420d27a6d468f7f269ded14 Mon Sep 17 00:00:00 2001
From: Mircea Trofin 
Date: Mon, 15 Sep 2025 17:49:18 +
Subject: [PATCH] [profcheck][SimplifyCFG] Propagate !prof from `switch` to
 `select`

---
 llvm/lib/Transforms/Utils/SimplifyCFG.cpp | 86 ---
 .../SimplifyCFG/switch-to-select-two-case.ll  | 72 +---
 2 files changed, 117 insertions(+), 41 deletions(-)

diff --git a/llvm/lib/Transforms/Utils/SimplifyCFG.cpp 
b/llvm/lib/Transforms/Utils/SimplifyCFG.cpp
index a1f759dd1df83..f775991b5ba41 100644
--- a/llvm/lib/Transforms/Utils/SimplifyCFG.cpp
+++ b/llvm/lib/Transforms/Utils/SimplifyCFG.cpp
@@ -84,6 +84,7 @@
 #include 
 #include 
 #include 
+#include 
 #include 
 #include 
 #include 
@@ -6318,9 +6319,12 @@ static bool initializeUniqueCases(SwitchInst *SI, 
PHINode *&PHI,
 // Helper function that checks if it is possible to transform a switch with 
only
 // two cases (or two cases + default) that produces a result into a select.
 // TODO: Handle switches with more than 2 cases that map to the same result.
+// The branch weights correspond to the provided Condition (i.e. if Condition 
is
+// modified from the original SwitchInst, the caller must adjust the weights)
 static Value *foldSwitchToSelect(const SwitchCaseResultVectorTy &ResultVector,
  Constant *DefaultResult, Value *Condition,
- IRBuilder<> &Builder, const DataLayout &DL) {
+ IRBuilder<> &Builder, const DataLayout &DL,
+ ArrayRef BranchWeights) {
   // If we are selecting between only two cases transform into a simple
   // select or a two-way select if default is possible.
   // Example:
@@ -6329,6 +6333,10 @@ static Value *foldSwitchToSelect(const 
SwitchCaseResultVectorTy &ResultVector,
   //   case 20: return 2;   >  %2 = icmp eq i32 %a, 20
   //   default: return 4;  %3 = select i1 %2, i32 2, i32 %1
   // }
+
+  const bool HasBranchWeights =
+  !BranchWeights.empty() && !ProfcheckDisableMetadataFixes;
+
   if (ResultVector.size() == 2 && ResultVector[0].second.size() == 1 &&
   ResultVector[1].second.size() == 1) {
 ConstantInt *FirstCase = ResultVector[0].second[0];
@@ -6337,13 +6345,37 @@ static Value *foldSwitchToSelect(const 
SwitchCaseResultVectorTy &ResultVector,
 if (DefaultResult) {
   Value *ValueCompare =
   Builder.CreateICmpEQ(Condition, SecondCase, "switch.selectcmp");
-  SelectValue = Builder.CreateSelect(ValueCompare, ResultVector[1].first,
- DefaultResult, "switch.select");
+  SelectInst *SelectValueInst = cast(Builder.CreateSelect(
+  ValueCompare, ResultVector[1].first, DefaultResult, 
"switch.select"));
+  SelectValue = SelectValueInst;
+  if (HasBranchWeights) {
+// We start with 3 probabilities, where the numerator is the
+// corresponding BranchWeights[i], and the denominator is the sum over
+// BranchWeights. We want the probability and negative probability of
+// Condition == SecondCase.
+assert(BranchWeights.size() == 3);
+setBranchWeights(SelectValueInst, BranchWeights[2],
+ BranchWeights[0] + BranchWeights[1],
+ /*IsExpected=*/false);
+  }
 }
 Value *ValueCompare =
 Builder.CreateICmpEQ(Condition, FirstCase, "switch.selectcmp");
-return Builder.CreateSelect(ValueCompare, ResultVector[0].first,
-SelectValue, "switch.select");
+SelectInst *Ret = cast(Builder.CreateSelect(
+ValueCompare, ResultVector[0].first, SelectValue, "switch.select"));
+if (HasBranchWeights) {
+  // We may have had a DefaultResult. Base the position of the first and
+  // second's branch weights accordingly. Also the proability that 
Condition
+  // != FirstCase needs to take that into account.
+  assert(BranchWeights.size() >= 2);
+  size_t FirstCasePos = (Condition != nullptr);
+  size_t SecondCasePos = FirstCasePos + 1;
+  uint32_t DefaultCase = (Condition != nullptr) ? BranchWeights[0] : 0;
+  setBranchWeights(Ret, BranchWeights[FirstCasePos],
+   DefaultCase + BranchWeights[SecondCasePos],
+   /*IsExpected=*/false);
+}
+return Ret;
   }
 
   // Handle the degenerate case where two cases have the same result value.
@@ -6379,8 +6411,16 @@ static Value *foldSwitchToSelect(const 
SwitchCaseResultVectorTy &ResultVector,
   Value *And = Builder.CreateAnd(Condition, AndMask);
   Value *Cmp = Builder.CreateICmpEQ(
   And, Constant::getIntegerValue(And->getType(), AndMask));
-  return Builder.CreateSelect(Cmp, ResultVector[0].first,
-  DefaultResult);
+  Select

[llvm-branch-commits] [llvm] [profcheck][SimplifyCFG] Propagate !prof from `switch` to `select` (PR #159645)

2025-09-24 Thread Mircea Trofin via llvm-branch-commits

mtrofin wrote:

> In general this patch LGTM.
> 
> I noticed that one downside of using `-profcheck-weights-for-test` is that 
> the original branch weights aren't in the test, so it's hard for me to 
> understand how this change modifies the branch weights.

You're right. I think I'll just use `-profcheck-weights-for-test` "offline" to 
generate the .ll that is checked in. It's a convenience anyway - to avoid one 
having to write interesting profile metadata by hand in large tests. wdyt?

https://github.com/llvm/llvm-project/pull/159645
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] [mlir][omp] Improve canonloop/iv naming (PR #159773)

2025-09-24 Thread Tom Eccles via llvm-branch-commits

https://github.com/tblah edited https://github.com/llvm/llvm-project/pull/159773
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] [mlir][omp] Improve canonloop/iv naming (PR #159773)

2025-09-24 Thread Tom Eccles via llvm-branch-commits


@@ -77,6 +77,177 @@ struct LLVMPointerPointerLikeModel
 };
 } // namespace
 
+/// Generate a name of a canonical loop nest of the format
+/// `(_s_r)*` that describes its nesting inside parent
+/// operations (`_r`) and that operation's region (`_s`). The region
+/// number is omitted if the parent operation has just one region. If a loop
+/// nest just consists of canonical loops nested inside each other, also uses
+/// `d` where  is the nesting depth of the loop.
+static std::string generateLoopNestingName(StringRef prefix,
+   CanonicalLoopOp op) {
+  struct Component {
+// An region argument of an operation
+Operation *parentOp;
+size_t regionInOpIdx;
+bool isOnlyRegionInOp;
+bool skipRegion;
+
+// An operation somewhere in a parent region
+Operation *thisOp;
+Region *parentRegion;
+size_t opInRegionIdx;
+bool isOnlyOpInRegion;
+bool skipOp;
+int depth = -1;
+  };
+  SmallVector components;
+
+  // Gather a list of parent regions and operations, and the position within
+  // their parent
+  Operation *o = op.getOperation();
+  while (o) {
+if (o->hasTrait())
+  break;
+
+// Operation within a region
+Region *r = o->getParentRegion();
+if (!r)
+  break;
+
+llvm::ReversePostOrderTraversal 
traversal(&r->getBlocks().front());
+size_t idx = 0;
+bool found = false;
+size_t sequentialIdx = -1;
+bool isOnlyLoop = true;
+for (Block *b : traversal) {
+  for (Operation &op : *b) {
+if (&op == o && !found) {
+  sequentialIdx = idx;
+  found = true;
+}
+if (op.getNumRegions()) {
+  idx += 1;
+  if (idx > 1)
+isOnlyLoop = false;
+}
+if (found && !isOnlyLoop)
+  break;
+  }
+}
+
+Component &comp = components.emplace_back();
+comp.thisOp = o;
+comp.parentRegion = r;
+comp.opInRegionIdx = sequentialIdx;
+comp.isOnlyOpInRegion = isOnlyLoop;

tblah wrote:

I think these names are a bit unclear.

An op containing regions doesn't mean that it is a loop. It could be an if 
statement or an openmp block construct etc.

isOnlyOpInRegion == true doesn't mean there aren't other ops in the region; it 
means that there aren't other ops containing regions in this region.

https://github.com/llvm/llvm-project/pull/159773
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] [mlir][omp] Improve canonloop/iv naming (PR #159773)

2025-09-24 Thread Tom Eccles via llvm-branch-commits


@@ -77,6 +77,177 @@ struct LLVMPointerPointerLikeModel
 };
 } // namespace
 
+/// Generate a name of a canonical loop nest of the format
+/// `(_s_r)*` that describes its nesting inside parent
+/// operations (`_r`) and that operation's region (`_s`). The region
+/// number is omitted if the parent operation has just one region. If a loop
+/// nest just consists of canonical loops nested inside each other, also uses
+/// `d` where  is the nesting depth of the loop.
+static std::string generateLoopNestingName(StringRef prefix,
+   CanonicalLoopOp op) {
+  struct Component {
+// An region argument of an operation
+Operation *parentOp;
+size_t regionInOpIdx;
+bool isOnlyRegionInOp;
+bool skipRegion;
+
+// An operation somewhere in a parent region
+Operation *thisOp;
+Region *parentRegion;
+size_t opInRegionIdx;
+bool isOnlyOpInRegion;
+bool skipOp;
+int depth = -1;
+  };
+  SmallVector components;
+
+  // Gather a list of parent regions and operations, and the position within
+  // their parent
+  Operation *o = op.getOperation();
+  while (o) {
+if (o->hasTrait())
+  break;
+
+// Operation within a region
+Region *r = o->getParentRegion();
+if (!r)
+  break;
+
+llvm::ReversePostOrderTraversal 
traversal(&r->getBlocks().front());
+size_t idx = 0;
+bool found = false;
+size_t sequentialIdx = -1;
+bool isOnlyLoop = true;
+for (Block *b : traversal) {
+  for (Operation &op : *b) {
+if (&op == o && !found) {
+  sequentialIdx = idx;
+  found = true;
+}
+if (op.getNumRegions()) {
+  idx += 1;
+  if (idx > 1)
+isOnlyLoop = false;
+}
+if (found && !isOnlyLoop)
+  break;
+  }
+}
+
+Component &comp = components.emplace_back();
+comp.thisOp = o;
+comp.parentRegion = r;
+comp.opInRegionIdx = sequentialIdx;
+comp.isOnlyOpInRegion = isOnlyLoop;
+
+// Region argument of an operation
+Operation *parent = r->getParentOp();
+
+comp.parentOp = parent;
+comp.regionInOpIdx = 0;
+comp.isOnlyRegionInOp = true;
+if (parent && parent->getRegions().size() > 1) {
+  auto getRegionIndex = [](Operation *o, Region *r) {
+for (auto [idx, region] : llvm::enumerate(o->getRegions())) {
+  if (®ion == r)
+return idx;
+}
+llvm_unreachable("Region not child of its parent operation");
+  };
+  comp.regionInOpIdx = getRegionIndex(parent, r);
+  comp.isOnlyRegionInOp = false;
+}
+
+if (!parent)
+  break;
+
+// next parent
+o = parent;
+  }
+
+  // Reorder components from outermost to innermost
+  std::reverse(components.begin(), components.end());

tblah wrote:

Unsure if it is worth doing given I wouldn't expect components to ever be that 
long, but the cost of this reversal could be avoided by just using backwards 
iterators in the following loops (where needed).

https://github.com/llvm/llvm-project/pull/159773
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm-remarkutil] Introduce summary tool (PR #160549)

2025-09-24 Thread Jon Roelofs via llvm-branch-commits


@@ -0,0 +1,244 @@
+//===- RemarkSummary.cpp 
--===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM 
Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===--===//
+//
+// Specialized tool to summarize remarks
+//
+//===--===//
+
+#include "RemarkUtilHelpers.h"
+#include "RemarkUtilRegistry.h"
+
+#include "llvm/ADT/STLExtras.h"
+#include "llvm/ADT/StringRef.h"
+#include "llvm/Support/CommandLine.h"
+#include "llvm/Support/Debug.h"
+#include "llvm/Support/Error.h"
+#include "llvm/Support/Regex.h"
+#include "llvm/Support/WithColor.h"
+#include 
+
+using namespace llvm;
+using namespace remarks;
+using namespace llvm::remarkutil;
+
+namespace summary {
+
+static cl::SubCommand
+SummarySub("summary", "Summarize Remarks using different strategies.");
+
+INPUT_FORMAT_COMMAND_LINE_OPTIONS(SummarySub)
+OUTPUT_FORMAT_COMMAND_LINE_OPTIONS(SummarySub)
+INPUT_OUTPUT_COMMAND_LINE_OPTIONS(SummarySub)
+
+static cl::OptionCategory SummaryStrategyCat("Strategy options");
+
+enum class KeepMode { None, Used, All };
+
+static cl::opt KeepInputOpt(
+"keep", cl::desc("Keep input remarks in output"), cl::init(KeepMode::None),
+cl::values(clEnumValN(KeepMode::None, "none",
+  "Don't keep input remarks (default)"),
+   clEnumValN(KeepMode::Used, "used",
+  "Keep only remarks used for summary"),
+   clEnumValN(KeepMode::All, "all", "Keep all input remarks")),
+cl::sub(SummarySub));
+
+static cl::opt
+IgnoreMalformedOpt("ignore-malformed",
+   cl::desc("Ignore remarks that fail to process"),
+   cl::init(false), cl::Hidden, cl::sub(SummarySub));
+
+// Use one cl::opt per Strategy, because future strategies might need to take
+// per-strategy parameters.
+static cl::opt EnableInlineSummaryOpt(

jroelofs wrote:

wdyt about making this a `cl::list>`? I think 
that would nicely support repeated summaries, like an optimization pipeline of 
sorts.

https://github.com/llvm/llvm-project/pull/160549
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm-remarkutil] Introduce summary tool (PR #160549)

2025-09-24 Thread Jon Roelofs via llvm-branch-commits


@@ -0,0 +1,244 @@
+//===- RemarkSummary.cpp 
--===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM 
Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===--===//
+//
+// Specialized tool to summarize remarks
+//
+//===--===//
+
+#include "RemarkUtilHelpers.h"
+#include "RemarkUtilRegistry.h"
+
+#include "llvm/ADT/STLExtras.h"
+#include "llvm/ADT/StringRef.h"
+#include "llvm/Support/CommandLine.h"
+#include "llvm/Support/Debug.h"
+#include "llvm/Support/Error.h"
+#include "llvm/Support/Regex.h"
+#include "llvm/Support/WithColor.h"
+#include 
+
+using namespace llvm;
+using namespace remarks;
+using namespace llvm::remarkutil;
+
+namespace summary {
+
+static cl::SubCommand
+SummarySub("summary", "Summarize Remarks using different strategies.");
+
+INPUT_FORMAT_COMMAND_LINE_OPTIONS(SummarySub)
+OUTPUT_FORMAT_COMMAND_LINE_OPTIONS(SummarySub)
+INPUT_OUTPUT_COMMAND_LINE_OPTIONS(SummarySub)
+
+static cl::OptionCategory SummaryStrategyCat("Strategy options");
+
+enum class KeepMode { None, Used, All };
+
+static cl::opt KeepInputOpt(
+"keep", cl::desc("Keep input remarks in output"), cl::init(KeepMode::None),
+cl::values(clEnumValN(KeepMode::None, "none",
+  "Don't keep input remarks (default)"),
+   clEnumValN(KeepMode::Used, "used",
+  "Keep only remarks used for summary"),
+   clEnumValN(KeepMode::All, "all", "Keep all input remarks")),
+cl::sub(SummarySub));
+
+static cl::opt
+IgnoreMalformedOpt("ignore-malformed",
+   cl::desc("Ignore remarks that fail to process"),
+   cl::init(false), cl::Hidden, cl::sub(SummarySub));
+
+// Use one cl::opt per Strategy, because future strategies might need to take
+// per-strategy parameters.
+static cl::opt EnableInlineSummaryOpt(
+"inline-callees", cl::desc("Summarize per-callee inling statistics"),
+cl::cat(SummaryStrategyCat), cl::init(false), cl::sub(SummarySub));
+
+class SummaryStrategy {
+public:
+  virtual ~SummaryStrategy() = default;
+  virtual bool filter(Remark &R) = 0;
+  virtual Error process(Remark &R) = 0;
+  virtual void emit(RemarkSerializer &Serializer) = 0;
+};

jroelofs wrote:

Some doxygen here describing the high-level expectations of this interface 
would be helpful.

https://github.com/llvm/llvm-project/pull/160549
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm-remarkutil] Introduce summary tool (PR #160549)

2025-09-24 Thread Jon Roelofs via llvm-branch-commits

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


https://github.com/llvm/llvm-project/pull/160549
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [libcxx] [libc++] Add accessor functions to __tree_node_base (PR #147679)

2025-09-24 Thread Louis Dionne via llvm-branch-commits


@@ -132,18 +139,18 @@ unsigned __tree_sub_invariant(_NodePtr __x) {
   if (__x->__left_ == __x->__right_ && __x->__left_ != nullptr)
 return 0;
   // If this is red, neither child can be red
-  if (!__x->__is_black_) {
-if (__x->__left_ && !__x->__left_->__is_black_)
+  if (__x->__color_ == __red) {
+if (__x->__left_ && __x->__left_->__color_ == __red)
   return 0;
-if (__x->__right_ && !__x->__right_->__is_black_)
+if (__x->__right_ && __x->__right_->__color_ == __red)
   return 0;
   }
   unsigned __h = std::__tree_sub_invariant(__x->__left_);
   if (__h == 0)
 return 0; // invalid left subtree
   if (__h != std::__tree_sub_invariant(__x->__right_))
 return 0;// invalid or different height right subtree
-  return __h + __x->__is_black_; // return black height of this node
+  return __h + (__x->__color_ == __black ? 1 : 0); // return black height of 
this node

ldionne wrote:

I think you should be using the accessor for getting the color here too.

https://github.com/llvm/llvm-project/pull/147679
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [libcxx] [libc++] Add accessor functions to __tree_node_base (PR #147679)

2025-09-24 Thread Louis Dionne via llvm-branch-commits

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

LGTM with nitpicks.

https://github.com/llvm/llvm-project/pull/147679
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] release/21.x: [NVPTX] Disable relative lookup tables (#159748) (PR #160064)

2025-09-24 Thread Artem Belevich via llvm-branch-commits

https://github.com/Artem-B edited 
https://github.com/llvm/llvm-project/pull/160064
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm-remarkutil] Introduce summary tool (PR #160549)

2025-09-24 Thread Jon Roelofs via llvm-branch-commits


@@ -34,6 +42,14 @@ std::optional Argument::getValAsInt() const {
   return KeyVal.getSExtValue();
 }
 
+std::optional Argument::getValAsSignedInt() const {

jroelofs wrote:

what's the difference between this and `getValAsInt`?

https://github.com/llvm/llvm-project/pull/160549
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [flang] [flang][OpenMP] Use OmpDirectiveSpecification in DECLARE_TARGET (PR #160573)

2025-09-24 Thread Krzysztof Parzyszek via llvm-branch-commits

https://github.com/kparzysz updated 
https://github.com/llvm/llvm-project/pull/160573

>From 525f12fa0da6c22dded6c19e2338b6bcc3c2da6f Mon Sep 17 00:00:00 2001
From: Krzysztof Parzyszek 
Date: Wed, 24 Sep 2025 07:59:16 -0500
Subject: [PATCH 1/2] [flang][OpenMP] Use OmpDirectiveSpecification in
 DECLARE_TARGET

---
 flang/include/flang/Parser/openmp-utils.h |   2 -
 flang/include/flang/Parser/parse-tree.h   |  10 +-
 flang/lib/Lower/OpenMP/OpenMP.cpp |  14 +-
 flang/lib/Parser/openmp-parsers.cpp   |  18 +-
 flang/lib/Parser/unparse.cpp  |   4 +-
 flang/lib/Semantics/check-omp-structure.cpp   | 245 +-
 flang/lib/Semantics/check-omp-structure.h |   3 -
 flang/lib/Semantics/resolve-directives.cpp|  27 +-
 flang/lib/Semantics/resolve-names.cpp |  77 +++---
 .../OpenMP/declare-target-indirect-tree.f90   |  28 +-
 .../OpenMP/declare-target-to-clause.f90   |  14 +-
 .../OpenMP/declare_target-device_type.f90 | 108 ++--
 .../Parser/OpenMP/enter-automap-modifier.f90  |  11 +-
 .../OpenMP/openmp6-directive-spellings.f90|   9 +-
 .../Semantics/OpenMP/blank-common-block.f90   |   1 +
 ...lare-target-function-name-with-symbols.f90 |   2 +-
 16 files changed, 319 insertions(+), 254 deletions(-)

diff --git a/flang/include/flang/Parser/openmp-utils.h 
b/flang/include/flang/Parser/openmp-utils.h
index 4b8fe6a5b49f0..bf54f970a7d3a 100644
--- a/flang/include/flang/Parser/openmp-utils.h
+++ b/flang/include/flang/Parser/openmp-utils.h
@@ -41,7 +41,6 @@ struct ConstructId {
 MAKE_CONSTR_ID(OpenMPDeclarativeAllocate, D::OMPD_allocate);
 MAKE_CONSTR_ID(OpenMPDeclarativeAssumes, D::OMPD_assumes);
 MAKE_CONSTR_ID(OpenMPDeclareReductionConstruct, D::OMPD_declare_reduction);
-MAKE_CONSTR_ID(OpenMPDeclareTargetConstruct, D::OMPD_declare_target);
 MAKE_CONSTR_ID(OpenMPExecutableAllocate, D::OMPD_allocate);
 MAKE_CONSTR_ID(OpenMPRequiresConstruct, D::OMPD_requires);
 
@@ -97,7 +96,6 @@ struct DirectiveNameScope {
   } else if constexpr (std::is_same_v ||
   std::is_same_v ||
   std::is_same_v ||
-  std::is_same_v ||
   std::is_same_v ||
   std::is_same_v) {
 return MakeName(std::get(x.t).source, ConstructId::id);
diff --git a/flang/include/flang/Parser/parse-tree.h 
b/flang/include/flang/Parser/parse-tree.h
index be30a95763208..e7593d9875097 100644
--- a/flang/include/flang/Parser/parse-tree.h
+++ b/flang/include/flang/Parser/parse-tree.h
@@ -4961,10 +4961,16 @@ struct OmpDeclareTargetSpecifier {
   std::variant u;
 };
 
+// Ref: [4.5:110-113], [5.0:180-185], [5.1:210-216], [5.2:206-207],
+//  [6.0:346-348]
+//
+// declare-target-directive ->  // since 4.5
+//DECLARE_TARGET[(extended-list)] |
+//DECLARE_TARGET clause-list
 struct OpenMPDeclareTargetConstruct {
-  TUPLE_CLASS_BOILERPLATE(OpenMPDeclareTargetConstruct);
+  WRAPPER_CLASS_BOILERPLATE(
+  OpenMPDeclareTargetConstruct, OmpDirectiveSpecification);
   CharBlock source;
-  std::tuple t;
 };
 
 // OMP v5.2: 5.8.8
diff --git a/flang/lib/Lower/OpenMP/OpenMP.cpp 
b/flang/lib/Lower/OpenMP/OpenMP.cpp
index d2e865b3e1d0c..1cb3335abbd06 100644
--- a/flang/lib/Lower/OpenMP/OpenMP.cpp
+++ b/flang/lib/Lower/OpenMP/OpenMP.cpp
@@ -761,19 +761,17 @@ static void promoteNonCPtrUseDevicePtrArgsToUseDeviceAddr(
 static void getDeclareTargetInfo(
 lower::AbstractConverter &converter, semantics::SemanticsContext &semaCtx,
 lower::pft::Evaluation &eval,
-const parser::OpenMPDeclareTargetConstruct &declareTargetConstruct,
+const parser::OpenMPDeclareTargetConstruct &construct,
 mlir::omp::DeclareTargetOperands &clauseOps,
 llvm::SmallVectorImpl &symbolAndClause) {
-  const auto &spec =
-  std::get(declareTargetConstruct.t);
-  if (const auto *objectList{parser::Unwrap(spec.u)}) {
-ObjectList objects{makeObjects(*objectList, semaCtx)};
+
+  if (!construct.v.Arguments().v.empty()) {
+ObjectList objects{makeObjects(construct.v.Arguments(), semaCtx)};
 // Case: declare target(func, var1, var2)
 gatherFuncAndVarSyms(objects, mlir::omp::DeclareTargetCaptureClause::to,
  symbolAndClause, /*automap=*/false);
-  } else if (const auto *clauseList{
- parser::Unwrap(spec.u)}) {
-List clauses = makeClauses(*clauseList, semaCtx);
+  } else {
+List clauses = makeClauses(construct.v.Clauses(), semaCtx);
 if (clauses.empty()) {
   Fortran::lower::pft::FunctionLikeUnit *owningProc =
   eval.getOwningProcedure();
diff --git a/flang/lib/Parser/openmp-parsers.cpp 
b/flang/lib/Parser/openmp-parsers.cpp
index 0085576292ff5..bd080386c0aea 100644
--- a/flang/lib/Parser/openmp-parsers.cpp
+++ b/flang/lib/Parser/openmp-parsers.cpp
@@ -1773,23 +1773,11 @@ 
TYPE_PARSER(sourced(construct(
 IsDirective(llvm::omp::Directive::OMPD_declare_reduction)) >=
 Parser{})))
 
-// declare-target with list
-TYPE_PARSER(sourced(construct(
-parenth

[llvm-branch-commits] [clang] [llvm] [DirectX] Updating Root Signature Metadata to contain Static Sampler flags (PR #160210)

2025-09-24 Thread via llvm-branch-commits

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

>From 6b191d041990ad667d86b6b07eeed7c802e3fe45 Mon Sep 17 00:00:00 2001
From: Joao Saffran 
Date: Mon, 22 Sep 2025 15:31:47 -0700
Subject: [PATCH 1/3] adding metadata static sampler flags

---
 clang/test/CodeGenHLSL/RootSignature.hlsl |  4 +-
 .../Frontend/HLSL/RootSignatureMetadata.cpp   | 14 +-
 ...gnature-StaticSamplers-Invalid-AddressU.ll |  2 +-
 ...gnature-StaticSamplers-Invalid-AddressV.ll |  2 +-
 ...gnature-StaticSamplers-Invalid-AddressW.ll |  2 +-
 ...ture-StaticSamplers-Invalid-BorderColor.ll |  2 +-
 ...e-StaticSamplers-Invalid-ComparisonFunc.ll |  2 +-
 ...Signature-StaticSamplers-Invalid-Filter.ll |  2 +-
 ...re-StaticSamplers-Invalid-MaxAnisotropy.ll |  2 +-
 ...Signature-StaticSamplers-Invalid-MaxLod.ll |  2 +-
 ...Signature-StaticSamplers-Invalid-MinLod.ll |  2 +-
 ...ature-StaticSamplers-Invalid-MinLopBias.ll |  2 +-
 ...re-StaticSamplers-Invalid-RegisterSpace.ll |  2 +-
 ...e-StaticSamplers-Invalid-ShaderRegister.ll |  2 +-
 ...StaticSamplers-Invalid-ShaderVisibility.ll |  2 +-
 .../RootSignature-StaticSamplers.ll   |  2 +-
 .../RootSignature-StaticSamplers_V3.ll| 43 +++
 .../rootsignature-validation-fail-sampler.ll  |  2 +-
 ...re-validation-fail-static-sampler-range.ll |  4 +-
 19 files changed, 75 insertions(+), 20 deletions(-)
 create mode 100644 
llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers_V3.ll

diff --git a/clang/test/CodeGenHLSL/RootSignature.hlsl 
b/clang/test/CodeGenHLSL/RootSignature.hlsl
index bc40bdd79ce59..bbab6a73a3658 100644
--- a/clang/test/CodeGenHLSL/RootSignature.hlsl
+++ b/clang/test/CodeGenHLSL/RootSignature.hlsl
@@ -82,8 +82,8 @@ void RootDescriptorsEntry() {}
 // checking minLOD, maxLOD
 // CHECK-SAME: float -1.28e+02, float 1.28e+02,
 
-// checking register, space and visibility
-// CHECK-SAME: i32 42, i32 0, i32 0}
+// checking register, space, visibility and flags
+// CHECK-SAME: i32 42, i32 0, i32 0, i32 0}
 
 #define SampleStaticSampler \
   "StaticSampler(s42, " \
diff --git a/llvm/lib/Frontend/HLSL/RootSignatureMetadata.cpp 
b/llvm/lib/Frontend/HLSL/RootSignatureMetadata.cpp
index f29f2c7602fc6..5ddf129265648 100644
--- a/llvm/lib/Frontend/HLSL/RootSignatureMetadata.cpp
+++ b/llvm/lib/Frontend/HLSL/RootSignatureMetadata.cpp
@@ -212,6 +212,7 @@ MDNode *MetadataBuilder::BuildStaticSampler(const 
StaticSampler &Sampler) {
   ConstantAsMetadata::get(Builder.getInt32(Sampler.Space)),
   ConstantAsMetadata::get(
   Builder.getInt32(to_underlying(Sampler.Visibility))),
+  ConstantAsMetadata::get(Builder.getInt32(0)),
   };
   return MDNode::get(Ctx, Operands);
 }
@@ -411,7 +412,7 @@ Error 
MetadataParser::parseDescriptorTable(mcdxbc::RootSignatureDesc &RSD,
 
 Error MetadataParser::parseStaticSampler(mcdxbc::RootSignatureDesc &RSD,
  MDNode *StaticSamplerNode) {
-  if (StaticSamplerNode->getNumOperands() != 14)
+  if (StaticSamplerNode->getNumOperands() != 15)
 return make_error("Static Sampler");
 
   mcdxbc::StaticSampler Sampler;
@@ -495,6 +496,17 @@ Error 
MetadataParser::parseStaticSampler(mcdxbc::RootSignatureDesc &RSD,
 return Error(std::move(E));
   Sampler.ShaderVisibility = *Visibility;
 
+  if (RSD.Version < 3) {
+RSD.StaticSamplers.push_back(Sampler);
+return Error::success();
+  }
+  assert(RSD.Version >= 3);
+
+  if (std::optional Val = extractMdIntValue(StaticSamplerNode, 14))
+Sampler.Flags = *Val;
+  else
+return make_error("Static Sampler Flags");
+
   RSD.StaticSamplers.push_back(Sampler);
   return Error::success();
 }
diff --git 
a/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers-Invalid-AddressU.ll
 
b/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers-Invalid-AddressU.ll
index 288dea00b6e55..b043ea1418df6 100644
--- 
a/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers-Invalid-AddressU.ll
+++ 
b/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers-Invalid-AddressU.ll
@@ -16,4 +16,4 @@ 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 = !{ !"StaticSampler", i32 4, i32 666, i32 3, i32 5, float 
0x3FF6C000, i32 9, i32 3, i32 2, float -1.28e+02, float 
1.28e+02, i32 42, i32 0, i32 0 }
+!5 = !{ !"StaticSampler", i32 4, i32 666, i32 3, i32 5, float 
0x3FF6C000, i32 9, i32 3, i32 2, float -1.28e+02, float 
1.28e+02, i32 42, i32 0, i32 0, i32 0 }
diff --git 
a/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers-Invalid-AddressV.ll
 
b/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers-Invalid-AddressV.ll
index e9abcf966..8219ffdd679d2 100644
--- 
a/llvm/test/CodeGen/D

[llvm-branch-commits] [clang] [llvm] [HLSL] Update Frontend to support version 1.2 of root signature (PR #160616)

2025-09-24 Thread Finn Plummer via llvm-branch-commits


@@ -926,6 +929,20 @@ RootSignatureParser::parseStaticSamplerParams() {
   if (!Visibility.has_value())
 return std::nullopt;
   Params.Visibility = Visibility;
+} else if (tryConsumeExpectedToken(TokenKind::kw_flags)) {
+  // `flags` `=` UINT_BORDER_COLOR

inbelic wrote:

nit:
```suggestion
  // `flags` `=` STATIC_SAMPLE_FLAGS
```

https://github.com/llvm/llvm-project/pull/160616
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [libunwind] release/21.x: [Mips] Fixed libunwind::Registers_mips_o32::jumpto to allow for load delay (#152942) (PR #160638)

2025-09-24 Thread via llvm-branch-commits

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

Backport a3d7c468bdc328f04da720088b2e542ef1f33ffc

Requested by: @brad0

>From 841de79c34154f7d96d1f74c60edfb6299bd7494 Mon Sep 17 00:00:00 2001
From: Jade Marker 
Date: Thu, 25 Sep 2025 02:20:25 +0100
Subject: [PATCH] [Mips] Fixed libunwind::Registers_mips_o32::jumpto to allow
 for load delay (#152942)

Fix #152922

MIPS III also has load delay, so
libunwind::Registers_mips_newabi::jumpto() is also fixed.

(cherry picked from commit a3d7c468bdc328f04da720088b2e542ef1f33ffc)
---
 libunwind/src/UnwindRegistersRestore.S | 7 +--
 1 file changed, 5 insertions(+), 2 deletions(-)

diff --git a/libunwind/src/UnwindRegistersRestore.S 
b/libunwind/src/UnwindRegistersRestore.S
index 5e199188945df..1bcd205be260d 100644
--- a/libunwind/src/UnwindRegistersRestore.S
+++ b/libunwind/src/UnwindRegistersRestore.S
@@ -1044,9 +1044,10 @@ 
DEFINE_LIBUNWIND_FUNCTION(_ZN9libunwind18Registers_mips_o326jumptoEv)
   lw$27, (4 * 27)($4)
   lw$28, (4 * 28)($4)
   lw$29, (4 * 29)($4)
-  lw$30, (4 * 30)($4)
   // load new pc into ra
   lw$31, (4 * 32)($4)
+  // MIPS 1 has load delay slot. Ensure lw $31 and jr are separated by an 
instruction.
+  lw$30, (4 * 30)($4)
   // jump to ra, load a0 in the delay slot
   jr$31
   lw$4, (4 * 4)($4)
@@ -1082,11 +1083,13 @@ 
DEFINE_LIBUNWIND_FUNCTION(_ZN9libunwind21Registers_mips_newabi6jumptoEv)
   ld$2, (8 * 2)($4)
   ld$3, (8 * 3)($4)
   // skip a0 for now
-  .irp 
i,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30
+  .irp i,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29
 ld $\i, (8 * \i)($4)
   .endr
   // load new pc into ra
   ld$31, (8 * 32)($4)
+  // MIPS 1 has load delay slot. Ensure lw $31 and jr are separated by an 
instruction.
+  ld$30, (8 * 30)($4)
   // jump to ra, load a0 in the delay slot
   jr$31
   ld$4, (8 * 4)($4)

___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [LifetimeSafety] Introduce a liveness-based lifetime policy (PR #159991)

2025-09-24 Thread Utkarsh Saxena via llvm-branch-commits

https://github.com/usx95 edited https://github.com/llvm/llvm-project/pull/159991
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [llvm] [HLSL] Update Frontend to support version 1.2 of root signature (PR #160616)

2025-09-24 Thread Finn Plummer via llvm-branch-commits


@@ -266,7 +266,8 @@ TEST(HLSLRootSignatureTest, DefaultStaticSamplerDump) {
  "minLOD = 0.00e+00, "
  "maxLOD = 3.402823e+38, "
  "space = 0, "
- "visibility = All"
+ "visibility = All, "
+ "flags = 0x0"

inbelic wrote:

These flags should be output with their named values (and `None` instead of 
`0`) to match the behaviour of the other flag types

https://github.com/llvm/llvm-project/pull/160616
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [llvm] [HLSL] Update Frontend to support version 1.2 of root signature (PR #160616)

2025-09-24 Thread Finn Plummer via llvm-branch-commits

https://github.com/inbelic edited 
https://github.com/llvm/llvm-project/pull/160616
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [libunwind] release/21.x: [Mips] Fixed libunwind::Registers_mips_o32::jumpto to allow for load delay (#152942) (PR #160638)

2025-09-24 Thread via llvm-branch-commits

llvmbot wrote:

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

https://github.com/llvm/llvm-project/pull/160638
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] [DirectX] Updating DXContainer logic to read version 1.2 of static samplers (PR #160184)

2025-09-24 Thread Justin Bogner via llvm-branch-commits

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

LGTM once @inbelic is happy with it

https://github.com/llvm/llvm-project/pull/160184
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [llvm] [DirectX] Updating Root Signature Metadata to contain Static Sampler flags (PR #160210)

2025-09-24 Thread Finn Plummer via llvm-branch-commits


@@ -212,6 +212,8 @@ MDNode *MetadataBuilder::BuildStaticSampler(const 
StaticSampler &Sampler) {
   ConstantAsMetadata::get(Builder.getInt32(Sampler.Space)),
   ConstantAsMetadata::get(
   Builder.getInt32(to_underlying(Sampler.Visibility))),
+  ConstantAsMetadata::get(
+Builder.getInt32(to_underlying(Sampler.Visibility))),

inbelic wrote:

```suggestion
Builder.getInt32(0)),
```
I think 0 makes more sense as the temporary measure

https://github.com/llvm/llvm-project/pull/160210
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] [DirectX] Updating DXContainer logic to read version 1.2 of static samplers (PR #160184)

2025-09-24 Thread via llvm-branch-commits

github-actions[bot] wrote:




:warning: C/C++ code formatter, clang-format found issues in your code. 
:warning:



You can test this locally with the following command:


``bash
git-clang-format --diff origin/main HEAD --extensions h,cpp -- 
llvm/include/llvm/Object/DXContainer.h llvm/lib/Object/DXContainer.cpp 
llvm/lib/ObjectYAML/DXContainerYAML.cpp 
llvm/unittests/Object/DXContainerTest.cpp
``

:warning:
The reproduction instructions above might return results for more than one PR
in a stack if you are using a stacked PR workflow. You can limit the results by
changing `origin/main` to the base branch/commit you want to compare against.
:warning:





View the diff from clang-format here.


``diff
diff --git a/llvm/lib/ObjectYAML/DXContainerYAML.cpp 
b/llvm/lib/ObjectYAML/DXContainerYAML.cpp
index efa8b40c2..3c09ae4e5 100644
--- a/llvm/lib/ObjectYAML/DXContainerYAML.cpp
+++ b/llvm/lib/ObjectYAML/DXContainerYAML.cpp
@@ -211,8 +211,7 @@ DXContainerYAML::RootSignatureYamlDesc::create(
 
 if (Version > 2) {
 #define STATIC_SAMPLER_FLAG(Num, Enum, Flag)   
\
-  NewS.Enum =  
\
-  (S.Flags & llvm::to_underlying(dxbc::StaticSamplerFlags::Enum));
+  NewS.Enum = (S.Flags & llvm::to_underlying(dxbc::StaticSamplerFlags::Enum));
 #include "llvm/BinaryFormat/DXContainerConstants.def"
 }
 RootSigDesc.StaticSamplers.push_back(NewS);
diff --git a/llvm/unittests/Object/DXContainerTest.cpp 
b/llvm/unittests/Object/DXContainerTest.cpp
index 9e805639c..d6f7b26b9 100644
--- a/llvm/unittests/Object/DXContainerTest.cpp
+++ b/llvm/unittests/Object/DXContainerTest.cpp
@@ -1201,8 +1201,8 @@ TEST(RootSignature, ParseStaticSamplers) {
 ASSERT_EQ(Sampler.ShaderVisibility, 7u);
   }
   {
-// this is testing static sampler parsing for root signature version 1.2, 
-// it changes: the version number, the size of root signature being 
emitted 
+// this is testing static sampler parsing for root signature version 1.2,
+// it changes: the version number, the size of root signature being emitted
 // and the values for flag fields.
 uint8_t Buffer[] = {
 0x44, 0x58, 0x42, 0x43, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,

``




https://github.com/llvm/llvm-project/pull/160184
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [flang] [flang][OpenMP] Use OmpDirectiveSpecification in ASSUMES (PR #160591)

2025-09-24 Thread via llvm-branch-commits

llvmbot wrote:




@llvm/pr-subscribers-flang-openmp

Author: Krzysztof Parzyszek (kparzysz)


Changes



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


6 Files Affected:

- (modified) flang/include/flang/Parser/openmp-utils.h (-2) 
- (modified) flang/include/flang/Parser/parse-tree.h (+2-2) 
- (modified) flang/lib/Parser/openmp-parsers.cpp (+4-2) 
- (modified) flang/lib/Parser/unparse.cpp (+2-2) 
- (modified) flang/lib/Semantics/check-omp-structure.cpp (-4) 
- (modified) flang/test/Parser/OpenMP/assumption.f90 (+5-3) 


``diff
diff --git a/flang/include/flang/Parser/openmp-utils.h 
b/flang/include/flang/Parser/openmp-utils.h
index bf54f970a7d3a..77c31b939e522 100644
--- a/flang/include/flang/Parser/openmp-utils.h
+++ b/flang/include/flang/Parser/openmp-utils.h
@@ -39,7 +39,6 @@ struct ConstructId {
   }
 
 MAKE_CONSTR_ID(OpenMPDeclarativeAllocate, D::OMPD_allocate);
-MAKE_CONSTR_ID(OpenMPDeclarativeAssumes, D::OMPD_assumes);
 MAKE_CONSTR_ID(OpenMPDeclareReductionConstruct, D::OMPD_declare_reduction);
 MAKE_CONSTR_ID(OpenMPExecutableAllocate, D::OMPD_allocate);
 MAKE_CONSTR_ID(OpenMPRequiresConstruct, D::OMPD_requires);
@@ -94,7 +93,6 @@ struct DirectiveNameScope {
   if constexpr (std::is_base_of_v) {
 return std::get(x.t).DirName();
   } else if constexpr (std::is_same_v ||
-  std::is_same_v ||
   std::is_same_v ||
   std::is_same_v ||
   std::is_same_v) {
diff --git a/flang/include/flang/Parser/parse-tree.h 
b/flang/include/flang/Parser/parse-tree.h
index 486be8b60ff8c..bd55166eb9f80 100644
--- a/flang/include/flang/Parser/parse-tree.h
+++ b/flang/include/flang/Parser/parse-tree.h
@@ -4877,8 +4877,8 @@ struct OpenMPUtilityConstruct {
 //   ASSUMES absent-clause | contains-clause | holds-clause | no-openmp-clause 
|
 //  no-openmp-routines-clause | no-parallelism-clause
 struct OpenMPDeclarativeAssumes {
-  TUPLE_CLASS_BOILERPLATE(OpenMPDeclarativeAssumes);
-  std::tuple t;
+  WRAPPER_CLASS_BOILERPLATE(
+  OpenMPDeclarativeAssumes, OmpDirectiveSpecification);
   CharBlock source;
 };
 
diff --git a/flang/lib/Parser/openmp-parsers.cpp 
b/flang/lib/Parser/openmp-parsers.cpp
index bd080386c0aea..12e89e8c35456 100644
--- a/flang/lib/Parser/openmp-parsers.cpp
+++ b/flang/lib/Parser/openmp-parsers.cpp
@@ -1852,8 +1852,10 @@ TYPE_PARSER(
 lookAhead(endOmpLine / !statement(allocateStmt)))
 
 // Assumes Construct
-TYPE_PARSER(sourced(construct(
-verbatim("ASSUMES"_tok), Parser{})))
+TYPE_PARSER(construct(
+predicated(OmpDirectiveNameParser{},
+IsDirective(llvm::omp::Directive::OMPD_assumes)) >=
+Parser{}))
 
 // Declarative constructs
 TYPE_PARSER(
diff --git a/flang/lib/Parser/unparse.cpp b/flang/lib/Parser/unparse.cpp
index a2b0b9ef3196c..9812a656092ac 100644
--- a/flang/lib/Parser/unparse.cpp
+++ b/flang/lib/Parser/unparse.cpp
@@ -2558,8 +2558,8 @@ class UnparseVisitor {
 
   void Unparse(const OpenMPDeclarativeAssumes &x) {
 BeginOpenMP();
-Word("!$OMP ASSUMES ");
-Walk(std::get(x.t));
+Word("!$OMP ");
+Walk(x.v);
 Put("\n");
 EndOpenMP();
   }
diff --git a/flang/lib/Semantics/check-omp-structure.cpp 
b/flang/lib/Semantics/check-omp-structure.cpp
index 05ff541657b1a..6538e0b794791 100644
--- a/flang/lib/Semantics/check-omp-structure.cpp
+++ b/flang/lib/Semantics/check-omp-structure.cpp
@@ -620,10 +620,6 @@ template  struct 
DirectiveSpellingVisitor {
 checker_(GetDirName(x.t).source, Directive::OMPD_allocators);
 return false;
   }
-  bool Pre(const parser::OpenMPDeclarativeAssumes &x) {
-checker_(std::get(x.t).source, Directive::OMPD_assumes);
-return false;
-  }
   bool Pre(const parser::OpenMPGroupprivate &x) {
 checker_(x.v.DirName().source, Directive::OMPD_groupprivate);
 return false;
diff --git a/flang/test/Parser/OpenMP/assumption.f90 
b/flang/test/Parser/OpenMP/assumption.f90
index 0f333f99f9085..86cbad9e42f78 100644
--- a/flang/test/Parser/OpenMP/assumption.f90
+++ b/flang/test/Parser/OpenMP/assumption.f90
@@ -141,9 +141,11 @@ program p
 end program p
 
 !UNPARSE: PROGRAM p
-!UNPARSE: !$OMP ASSUMES  NO_OPENMP
+!UNPARSE: !$OMP ASSUMES NO_OPENMP
 !UNPARSE: END PROGRAM p
 
-!PARSE-TREE: OpenMPDeclarativeConstruct -> OpenMPDeclarativeAssumes
-!PARSE-TREE: | Verbatim
+!PARSE-TREE: OpenMPDeclarativeConstruct -> OpenMPDeclarativeAssumes -> 
OmpDirectiveSpecification
+!PARSE-TREE: | OmpDirectiveName -> llvm::omp::Directive = assumes
 !PARSE-TREE: | OmpClauseList -> OmpClause -> NoOpenmp
+!PARSE-TREE: | Flags = None
+!PARSE-TREE: ImplicitPart ->

``




https://github.com/llvm/llvm-project/pull/160591
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [flang] [flang][OpenMP] Use OmpDirectiveSpecification in ASSUMES (PR #160591)

2025-09-24 Thread via llvm-branch-commits

llvmbot wrote:




@llvm/pr-subscribers-flang-semantics

Author: Krzysztof Parzyszek (kparzysz)


Changes



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


6 Files Affected:

- (modified) flang/include/flang/Parser/openmp-utils.h (-2) 
- (modified) flang/include/flang/Parser/parse-tree.h (+2-2) 
- (modified) flang/lib/Parser/openmp-parsers.cpp (+4-2) 
- (modified) flang/lib/Parser/unparse.cpp (+2-2) 
- (modified) flang/lib/Semantics/check-omp-structure.cpp (-4) 
- (modified) flang/test/Parser/OpenMP/assumption.f90 (+5-3) 


``diff
diff --git a/flang/include/flang/Parser/openmp-utils.h 
b/flang/include/flang/Parser/openmp-utils.h
index bf54f970a7d3a..77c31b939e522 100644
--- a/flang/include/flang/Parser/openmp-utils.h
+++ b/flang/include/flang/Parser/openmp-utils.h
@@ -39,7 +39,6 @@ struct ConstructId {
   }
 
 MAKE_CONSTR_ID(OpenMPDeclarativeAllocate, D::OMPD_allocate);
-MAKE_CONSTR_ID(OpenMPDeclarativeAssumes, D::OMPD_assumes);
 MAKE_CONSTR_ID(OpenMPDeclareReductionConstruct, D::OMPD_declare_reduction);
 MAKE_CONSTR_ID(OpenMPExecutableAllocate, D::OMPD_allocate);
 MAKE_CONSTR_ID(OpenMPRequiresConstruct, D::OMPD_requires);
@@ -94,7 +93,6 @@ struct DirectiveNameScope {
   if constexpr (std::is_base_of_v) {
 return std::get(x.t).DirName();
   } else if constexpr (std::is_same_v ||
-  std::is_same_v ||
   std::is_same_v ||
   std::is_same_v ||
   std::is_same_v) {
diff --git a/flang/include/flang/Parser/parse-tree.h 
b/flang/include/flang/Parser/parse-tree.h
index 486be8b60ff8c..bd55166eb9f80 100644
--- a/flang/include/flang/Parser/parse-tree.h
+++ b/flang/include/flang/Parser/parse-tree.h
@@ -4877,8 +4877,8 @@ struct OpenMPUtilityConstruct {
 //   ASSUMES absent-clause | contains-clause | holds-clause | no-openmp-clause 
|
 //  no-openmp-routines-clause | no-parallelism-clause
 struct OpenMPDeclarativeAssumes {
-  TUPLE_CLASS_BOILERPLATE(OpenMPDeclarativeAssumes);
-  std::tuple t;
+  WRAPPER_CLASS_BOILERPLATE(
+  OpenMPDeclarativeAssumes, OmpDirectiveSpecification);
   CharBlock source;
 };
 
diff --git a/flang/lib/Parser/openmp-parsers.cpp 
b/flang/lib/Parser/openmp-parsers.cpp
index bd080386c0aea..12e89e8c35456 100644
--- a/flang/lib/Parser/openmp-parsers.cpp
+++ b/flang/lib/Parser/openmp-parsers.cpp
@@ -1852,8 +1852,10 @@ TYPE_PARSER(
 lookAhead(endOmpLine / !statement(allocateStmt)))
 
 // Assumes Construct
-TYPE_PARSER(sourced(construct(
-verbatim("ASSUMES"_tok), Parser{})))
+TYPE_PARSER(construct(
+predicated(OmpDirectiveNameParser{},
+IsDirective(llvm::omp::Directive::OMPD_assumes)) >=
+Parser{}))
 
 // Declarative constructs
 TYPE_PARSER(
diff --git a/flang/lib/Parser/unparse.cpp b/flang/lib/Parser/unparse.cpp
index a2b0b9ef3196c..9812a656092ac 100644
--- a/flang/lib/Parser/unparse.cpp
+++ b/flang/lib/Parser/unparse.cpp
@@ -2558,8 +2558,8 @@ class UnparseVisitor {
 
   void Unparse(const OpenMPDeclarativeAssumes &x) {
 BeginOpenMP();
-Word("!$OMP ASSUMES ");
-Walk(std::get(x.t));
+Word("!$OMP ");
+Walk(x.v);
 Put("\n");
 EndOpenMP();
   }
diff --git a/flang/lib/Semantics/check-omp-structure.cpp 
b/flang/lib/Semantics/check-omp-structure.cpp
index 05ff541657b1a..6538e0b794791 100644
--- a/flang/lib/Semantics/check-omp-structure.cpp
+++ b/flang/lib/Semantics/check-omp-structure.cpp
@@ -620,10 +620,6 @@ template  struct 
DirectiveSpellingVisitor {
 checker_(GetDirName(x.t).source, Directive::OMPD_allocators);
 return false;
   }
-  bool Pre(const parser::OpenMPDeclarativeAssumes &x) {
-checker_(std::get(x.t).source, Directive::OMPD_assumes);
-return false;
-  }
   bool Pre(const parser::OpenMPGroupprivate &x) {
 checker_(x.v.DirName().source, Directive::OMPD_groupprivate);
 return false;
diff --git a/flang/test/Parser/OpenMP/assumption.f90 
b/flang/test/Parser/OpenMP/assumption.f90
index 0f333f99f9085..86cbad9e42f78 100644
--- a/flang/test/Parser/OpenMP/assumption.f90
+++ b/flang/test/Parser/OpenMP/assumption.f90
@@ -141,9 +141,11 @@ program p
 end program p
 
 !UNPARSE: PROGRAM p
-!UNPARSE: !$OMP ASSUMES  NO_OPENMP
+!UNPARSE: !$OMP ASSUMES NO_OPENMP
 !UNPARSE: END PROGRAM p
 
-!PARSE-TREE: OpenMPDeclarativeConstruct -> OpenMPDeclarativeAssumes
-!PARSE-TREE: | Verbatim
+!PARSE-TREE: OpenMPDeclarativeConstruct -> OpenMPDeclarativeAssumes -> 
OmpDirectiveSpecification
+!PARSE-TREE: | OmpDirectiveName -> llvm::omp::Directive = assumes
 !PARSE-TREE: | OmpClauseList -> OmpClause -> NoOpenmp
+!PARSE-TREE: | Flags = None
+!PARSE-TREE: ImplicitPart ->

``




https://github.com/llvm/llvm-project/pull/160591
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] [DirectX] Updating DXContainer logic to read version 1.2 of static samplers (PR #160184)

2025-09-24 Thread Finn Plummer via llvm-branch-commits

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


https://github.com/llvm/llvm-project/pull/160184
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [flang] [flang][OpenMP] Use OmpDirectiveSpecification in ASSUMES (PR #160591)

2025-09-24 Thread Krzysztof Parzyszek via llvm-branch-commits

https://github.com/kparzysz updated 
https://github.com/llvm/llvm-project/pull/160591

>From eb12400ffc25b62205183f3102a1e0afdb785510 Mon Sep 17 00:00:00 2001
From: Krzysztof Parzyszek 
Date: Wed, 24 Sep 2025 14:38:40 -0500
Subject: [PATCH 1/2] [flang][OpenMP] Use OmpDirectiveSpecification in ASSUMES

---
 flang/include/flang/Parser/openmp-utils.h   | 2 --
 flang/include/flang/Parser/parse-tree.h | 4 ++--
 flang/lib/Parser/openmp-parsers.cpp | 6 --
 flang/lib/Parser/unparse.cpp| 4 ++--
 flang/lib/Semantics/check-omp-structure.cpp | 4 
 flang/test/Parser/OpenMP/assumption.f90 | 8 +---
 6 files changed, 13 insertions(+), 15 deletions(-)

diff --git a/flang/include/flang/Parser/openmp-utils.h 
b/flang/include/flang/Parser/openmp-utils.h
index bf54f970a7d3a..77c31b939e522 100644
--- a/flang/include/flang/Parser/openmp-utils.h
+++ b/flang/include/flang/Parser/openmp-utils.h
@@ -39,7 +39,6 @@ struct ConstructId {
   }
 
 MAKE_CONSTR_ID(OpenMPDeclarativeAllocate, D::OMPD_allocate);
-MAKE_CONSTR_ID(OpenMPDeclarativeAssumes, D::OMPD_assumes);
 MAKE_CONSTR_ID(OpenMPDeclareReductionConstruct, D::OMPD_declare_reduction);
 MAKE_CONSTR_ID(OpenMPExecutableAllocate, D::OMPD_allocate);
 MAKE_CONSTR_ID(OpenMPRequiresConstruct, D::OMPD_requires);
@@ -94,7 +93,6 @@ struct DirectiveNameScope {
   if constexpr (std::is_base_of_v) {
 return std::get(x.t).DirName();
   } else if constexpr (std::is_same_v ||
-  std::is_same_v ||
   std::is_same_v ||
   std::is_same_v ||
   std::is_same_v) {
diff --git a/flang/include/flang/Parser/parse-tree.h 
b/flang/include/flang/Parser/parse-tree.h
index 486be8b60ff8c..bd55166eb9f80 100644
--- a/flang/include/flang/Parser/parse-tree.h
+++ b/flang/include/flang/Parser/parse-tree.h
@@ -4877,8 +4877,8 @@ struct OpenMPUtilityConstruct {
 //   ASSUMES absent-clause | contains-clause | holds-clause | no-openmp-clause 
|
 //  no-openmp-routines-clause | no-parallelism-clause
 struct OpenMPDeclarativeAssumes {
-  TUPLE_CLASS_BOILERPLATE(OpenMPDeclarativeAssumes);
-  std::tuple t;
+  WRAPPER_CLASS_BOILERPLATE(
+  OpenMPDeclarativeAssumes, OmpDirectiveSpecification);
   CharBlock source;
 };
 
diff --git a/flang/lib/Parser/openmp-parsers.cpp 
b/flang/lib/Parser/openmp-parsers.cpp
index bd080386c0aea..12e89e8c35456 100644
--- a/flang/lib/Parser/openmp-parsers.cpp
+++ b/flang/lib/Parser/openmp-parsers.cpp
@@ -1852,8 +1852,10 @@ TYPE_PARSER(
 lookAhead(endOmpLine / !statement(allocateStmt)))
 
 // Assumes Construct
-TYPE_PARSER(sourced(construct(
-verbatim("ASSUMES"_tok), Parser{})))
+TYPE_PARSER(construct(
+predicated(OmpDirectiveNameParser{},
+IsDirective(llvm::omp::Directive::OMPD_assumes)) >=
+Parser{}))
 
 // Declarative constructs
 TYPE_PARSER(
diff --git a/flang/lib/Parser/unparse.cpp b/flang/lib/Parser/unparse.cpp
index a2b0b9ef3196c..9812a656092ac 100644
--- a/flang/lib/Parser/unparse.cpp
+++ b/flang/lib/Parser/unparse.cpp
@@ -2558,8 +2558,8 @@ class UnparseVisitor {
 
   void Unparse(const OpenMPDeclarativeAssumes &x) {
 BeginOpenMP();
-Word("!$OMP ASSUMES ");
-Walk(std::get(x.t));
+Word("!$OMP ");
+Walk(x.v);
 Put("\n");
 EndOpenMP();
   }
diff --git a/flang/lib/Semantics/check-omp-structure.cpp 
b/flang/lib/Semantics/check-omp-structure.cpp
index 05ff541657b1a..6538e0b794791 100644
--- a/flang/lib/Semantics/check-omp-structure.cpp
+++ b/flang/lib/Semantics/check-omp-structure.cpp
@@ -620,10 +620,6 @@ template  struct 
DirectiveSpellingVisitor {
 checker_(GetDirName(x.t).source, Directive::OMPD_allocators);
 return false;
   }
-  bool Pre(const parser::OpenMPDeclarativeAssumes &x) {
-checker_(std::get(x.t).source, Directive::OMPD_assumes);
-return false;
-  }
   bool Pre(const parser::OpenMPGroupprivate &x) {
 checker_(x.v.DirName().source, Directive::OMPD_groupprivate);
 return false;
diff --git a/flang/test/Parser/OpenMP/assumption.f90 
b/flang/test/Parser/OpenMP/assumption.f90
index 0f333f99f9085..86cbad9e42f78 100644
--- a/flang/test/Parser/OpenMP/assumption.f90
+++ b/flang/test/Parser/OpenMP/assumption.f90
@@ -141,9 +141,11 @@ program p
 end program p
 
 !UNPARSE: PROGRAM p
-!UNPARSE: !$OMP ASSUMES  NO_OPENMP
+!UNPARSE: !$OMP ASSUMES NO_OPENMP
 !UNPARSE: END PROGRAM p
 
-!PARSE-TREE: OpenMPDeclarativeConstruct -> OpenMPDeclarativeAssumes
-!PARSE-TREE: | Verbatim
+!PARSE-TREE: OpenMPDeclarativeConstruct -> OpenMPDeclarativeAssumes -> 
OmpDirectiveSpecification
+!PARSE-TREE: | OmpDirectiveName -> llvm::omp::Directive = assumes
 !PARSE-TREE: | OmpClauseList -> OmpClause -> NoOpenmp
+!PARSE-TREE: | Flags = None
+!PARSE-TREE: ImplicitPart ->

>From 7f1df5bd47499d75180ba2c8509730e4bba60956 Mon Sep 17 00:00:00 2001
From: Krzysztof Parzyszek 
Date: Wed, 24 Sep 2025 14:49:35 -0500
Subject: [PATCH 2/2] Forgot "sourced"

---
 flang/lib/Parser/openmp-parsers.cpp | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff 

[llvm-branch-commits] [flang] [flang][OpenMP] Use OmpDirectiveSpecification in DECLARE_TARGET (PR #160573)

2025-09-24 Thread Krzysztof Parzyszek via llvm-branch-commits

https://github.com/kparzysz updated 
https://github.com/llvm/llvm-project/pull/160573

>From 525f12fa0da6c22dded6c19e2338b6bcc3c2da6f Mon Sep 17 00:00:00 2001
From: Krzysztof Parzyszek 
Date: Wed, 24 Sep 2025 07:59:16 -0500
Subject: [PATCH 1/4] [flang][OpenMP] Use OmpDirectiveSpecification in
 DECLARE_TARGET

---
 flang/include/flang/Parser/openmp-utils.h |   2 -
 flang/include/flang/Parser/parse-tree.h   |  10 +-
 flang/lib/Lower/OpenMP/OpenMP.cpp |  14 +-
 flang/lib/Parser/openmp-parsers.cpp   |  18 +-
 flang/lib/Parser/unparse.cpp  |   4 +-
 flang/lib/Semantics/check-omp-structure.cpp   | 245 +-
 flang/lib/Semantics/check-omp-structure.h |   3 -
 flang/lib/Semantics/resolve-directives.cpp|  27 +-
 flang/lib/Semantics/resolve-names.cpp |  77 +++---
 .../OpenMP/declare-target-indirect-tree.f90   |  28 +-
 .../OpenMP/declare-target-to-clause.f90   |  14 +-
 .../OpenMP/declare_target-device_type.f90 | 108 ++--
 .../Parser/OpenMP/enter-automap-modifier.f90  |  11 +-
 .../OpenMP/openmp6-directive-spellings.f90|   9 +-
 .../Semantics/OpenMP/blank-common-block.f90   |   1 +
 ...lare-target-function-name-with-symbols.f90 |   2 +-
 16 files changed, 319 insertions(+), 254 deletions(-)

diff --git a/flang/include/flang/Parser/openmp-utils.h 
b/flang/include/flang/Parser/openmp-utils.h
index 4b8fe6a5b49f0..bf54f970a7d3a 100644
--- a/flang/include/flang/Parser/openmp-utils.h
+++ b/flang/include/flang/Parser/openmp-utils.h
@@ -41,7 +41,6 @@ struct ConstructId {
 MAKE_CONSTR_ID(OpenMPDeclarativeAllocate, D::OMPD_allocate);
 MAKE_CONSTR_ID(OpenMPDeclarativeAssumes, D::OMPD_assumes);
 MAKE_CONSTR_ID(OpenMPDeclareReductionConstruct, D::OMPD_declare_reduction);
-MAKE_CONSTR_ID(OpenMPDeclareTargetConstruct, D::OMPD_declare_target);
 MAKE_CONSTR_ID(OpenMPExecutableAllocate, D::OMPD_allocate);
 MAKE_CONSTR_ID(OpenMPRequiresConstruct, D::OMPD_requires);
 
@@ -97,7 +96,6 @@ struct DirectiveNameScope {
   } else if constexpr (std::is_same_v ||
   std::is_same_v ||
   std::is_same_v ||
-  std::is_same_v ||
   std::is_same_v ||
   std::is_same_v) {
 return MakeName(std::get(x.t).source, ConstructId::id);
diff --git a/flang/include/flang/Parser/parse-tree.h 
b/flang/include/flang/Parser/parse-tree.h
index be30a95763208..e7593d9875097 100644
--- a/flang/include/flang/Parser/parse-tree.h
+++ b/flang/include/flang/Parser/parse-tree.h
@@ -4961,10 +4961,16 @@ struct OmpDeclareTargetSpecifier {
   std::variant u;
 };
 
+// Ref: [4.5:110-113], [5.0:180-185], [5.1:210-216], [5.2:206-207],
+//  [6.0:346-348]
+//
+// declare-target-directive ->  // since 4.5
+//DECLARE_TARGET[(extended-list)] |
+//DECLARE_TARGET clause-list
 struct OpenMPDeclareTargetConstruct {
-  TUPLE_CLASS_BOILERPLATE(OpenMPDeclareTargetConstruct);
+  WRAPPER_CLASS_BOILERPLATE(
+  OpenMPDeclareTargetConstruct, OmpDirectiveSpecification);
   CharBlock source;
-  std::tuple t;
 };
 
 // OMP v5.2: 5.8.8
diff --git a/flang/lib/Lower/OpenMP/OpenMP.cpp 
b/flang/lib/Lower/OpenMP/OpenMP.cpp
index d2e865b3e1d0c..1cb3335abbd06 100644
--- a/flang/lib/Lower/OpenMP/OpenMP.cpp
+++ b/flang/lib/Lower/OpenMP/OpenMP.cpp
@@ -761,19 +761,17 @@ static void promoteNonCPtrUseDevicePtrArgsToUseDeviceAddr(
 static void getDeclareTargetInfo(
 lower::AbstractConverter &converter, semantics::SemanticsContext &semaCtx,
 lower::pft::Evaluation &eval,
-const parser::OpenMPDeclareTargetConstruct &declareTargetConstruct,
+const parser::OpenMPDeclareTargetConstruct &construct,
 mlir::omp::DeclareTargetOperands &clauseOps,
 llvm::SmallVectorImpl &symbolAndClause) {
-  const auto &spec =
-  std::get(declareTargetConstruct.t);
-  if (const auto *objectList{parser::Unwrap(spec.u)}) {
-ObjectList objects{makeObjects(*objectList, semaCtx)};
+
+  if (!construct.v.Arguments().v.empty()) {
+ObjectList objects{makeObjects(construct.v.Arguments(), semaCtx)};
 // Case: declare target(func, var1, var2)
 gatherFuncAndVarSyms(objects, mlir::omp::DeclareTargetCaptureClause::to,
  symbolAndClause, /*automap=*/false);
-  } else if (const auto *clauseList{
- parser::Unwrap(spec.u)}) {
-List clauses = makeClauses(*clauseList, semaCtx);
+  } else {
+List clauses = makeClauses(construct.v.Clauses(), semaCtx);
 if (clauses.empty()) {
   Fortran::lower::pft::FunctionLikeUnit *owningProc =
   eval.getOwningProcedure();
diff --git a/flang/lib/Parser/openmp-parsers.cpp 
b/flang/lib/Parser/openmp-parsers.cpp
index 0085576292ff5..bd080386c0aea 100644
--- a/flang/lib/Parser/openmp-parsers.cpp
+++ b/flang/lib/Parser/openmp-parsers.cpp
@@ -1773,23 +1773,11 @@ 
TYPE_PARSER(sourced(construct(
 IsDirective(llvm::omp::Directive::OMPD_declare_reduction)) >=
 Parser{})))
 
-// declare-target with list
-TYPE_PARSER(sourced(construct(
-parenth

[llvm-branch-commits] [libcxx] [libc++] Add accessor functions to __tree_node_base (PR #147679)

2025-09-24 Thread Louis Dionne via llvm-branch-commits

https://github.com/ldionne edited 
https://github.com/llvm/llvm-project/pull/147679
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] Greedy: Move physreg check when trying to recolor vregs (NFC) (PR #160484)

2025-09-24 Thread Philip Reames via llvm-branch-commits

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

LGTM

https://github.com/llvm/llvm-project/pull/160484
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm-remarkutil] Introduce summary tool (PR #160549)

2025-09-24 Thread Tobias Stadler via llvm-branch-commits

https://github.com/tobias-stadler created 
https://github.com/llvm/llvm-project/pull/160549

This tool provides a harness for implementing different strategies that
summarize many remarks (possibly from multiple translation units) into
new summary remarks. The remark summaries can then be viewed using tools
like `opt-viewer`.

The first summary strategy is `--inline-callees`, which generates
remarks that summarize the per-callee inline statistics for functions
that appear in inling remarks. This is useful for troubleshooting
inlining issues/regressions on large codebases.



___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] Greedy: Merge VirtRegMap queries into one use (NFC) (PR #160485)

2025-09-24 Thread Philip Reames via llvm-branch-commits

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

LGTM

https://github.com/llvm/llvm-project/pull/160485
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [llvm] [DirectX] Updating Root Signature Metadata to contain Static Sampler flags (PR #160210)

2025-09-24 Thread via llvm-branch-commits

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

>From 6b191d041990ad667d86b6b07eeed7c802e3fe45 Mon Sep 17 00:00:00 2001
From: Joao Saffran 
Date: Mon, 22 Sep 2025 15:31:47 -0700
Subject: [PATCH 1/5] adding metadata static sampler flags

---
 clang/test/CodeGenHLSL/RootSignature.hlsl |  4 +-
 .../Frontend/HLSL/RootSignatureMetadata.cpp   | 14 +-
 ...gnature-StaticSamplers-Invalid-AddressU.ll |  2 +-
 ...gnature-StaticSamplers-Invalid-AddressV.ll |  2 +-
 ...gnature-StaticSamplers-Invalid-AddressW.ll |  2 +-
 ...ture-StaticSamplers-Invalid-BorderColor.ll |  2 +-
 ...e-StaticSamplers-Invalid-ComparisonFunc.ll |  2 +-
 ...Signature-StaticSamplers-Invalid-Filter.ll |  2 +-
 ...re-StaticSamplers-Invalid-MaxAnisotropy.ll |  2 +-
 ...Signature-StaticSamplers-Invalid-MaxLod.ll |  2 +-
 ...Signature-StaticSamplers-Invalid-MinLod.ll |  2 +-
 ...ature-StaticSamplers-Invalid-MinLopBias.ll |  2 +-
 ...re-StaticSamplers-Invalid-RegisterSpace.ll |  2 +-
 ...e-StaticSamplers-Invalid-ShaderRegister.ll |  2 +-
 ...StaticSamplers-Invalid-ShaderVisibility.ll |  2 +-
 .../RootSignature-StaticSamplers.ll   |  2 +-
 .../RootSignature-StaticSamplers_V3.ll| 43 +++
 .../rootsignature-validation-fail-sampler.ll  |  2 +-
 ...re-validation-fail-static-sampler-range.ll |  4 +-
 19 files changed, 75 insertions(+), 20 deletions(-)
 create mode 100644 
llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers_V3.ll

diff --git a/clang/test/CodeGenHLSL/RootSignature.hlsl 
b/clang/test/CodeGenHLSL/RootSignature.hlsl
index bc40bdd79ce59..bbab6a73a3658 100644
--- a/clang/test/CodeGenHLSL/RootSignature.hlsl
+++ b/clang/test/CodeGenHLSL/RootSignature.hlsl
@@ -82,8 +82,8 @@ void RootDescriptorsEntry() {}
 // checking minLOD, maxLOD
 // CHECK-SAME: float -1.28e+02, float 1.28e+02,
 
-// checking register, space and visibility
-// CHECK-SAME: i32 42, i32 0, i32 0}
+// checking register, space, visibility and flags
+// CHECK-SAME: i32 42, i32 0, i32 0, i32 0}
 
 #define SampleStaticSampler \
   "StaticSampler(s42, " \
diff --git a/llvm/lib/Frontend/HLSL/RootSignatureMetadata.cpp 
b/llvm/lib/Frontend/HLSL/RootSignatureMetadata.cpp
index f29f2c7602fc6..5ddf129265648 100644
--- a/llvm/lib/Frontend/HLSL/RootSignatureMetadata.cpp
+++ b/llvm/lib/Frontend/HLSL/RootSignatureMetadata.cpp
@@ -212,6 +212,7 @@ MDNode *MetadataBuilder::BuildStaticSampler(const 
StaticSampler &Sampler) {
   ConstantAsMetadata::get(Builder.getInt32(Sampler.Space)),
   ConstantAsMetadata::get(
   Builder.getInt32(to_underlying(Sampler.Visibility))),
+  ConstantAsMetadata::get(Builder.getInt32(0)),
   };
   return MDNode::get(Ctx, Operands);
 }
@@ -411,7 +412,7 @@ Error 
MetadataParser::parseDescriptorTable(mcdxbc::RootSignatureDesc &RSD,
 
 Error MetadataParser::parseStaticSampler(mcdxbc::RootSignatureDesc &RSD,
  MDNode *StaticSamplerNode) {
-  if (StaticSamplerNode->getNumOperands() != 14)
+  if (StaticSamplerNode->getNumOperands() != 15)
 return make_error("Static Sampler");
 
   mcdxbc::StaticSampler Sampler;
@@ -495,6 +496,17 @@ Error 
MetadataParser::parseStaticSampler(mcdxbc::RootSignatureDesc &RSD,
 return Error(std::move(E));
   Sampler.ShaderVisibility = *Visibility;
 
+  if (RSD.Version < 3) {
+RSD.StaticSamplers.push_back(Sampler);
+return Error::success();
+  }
+  assert(RSD.Version >= 3);
+
+  if (std::optional Val = extractMdIntValue(StaticSamplerNode, 14))
+Sampler.Flags = *Val;
+  else
+return make_error("Static Sampler Flags");
+
   RSD.StaticSamplers.push_back(Sampler);
   return Error::success();
 }
diff --git 
a/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers-Invalid-AddressU.ll
 
b/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers-Invalid-AddressU.ll
index 288dea00b6e55..b043ea1418df6 100644
--- 
a/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers-Invalid-AddressU.ll
+++ 
b/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers-Invalid-AddressU.ll
@@ -16,4 +16,4 @@ 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 = !{ !"StaticSampler", i32 4, i32 666, i32 3, i32 5, float 
0x3FF6C000, i32 9, i32 3, i32 2, float -1.28e+02, float 
1.28e+02, i32 42, i32 0, i32 0 }
+!5 = !{ !"StaticSampler", i32 4, i32 666, i32 3, i32 5, float 
0x3FF6C000, i32 9, i32 3, i32 2, float -1.28e+02, float 
1.28e+02, i32 42, i32 0, i32 0, i32 0 }
diff --git 
a/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers-Invalid-AddressV.ll
 
b/llvm/test/CodeGen/DirectX/ContainerData/RootSignature-StaticSamplers-Invalid-AddressV.ll
index e9abcf966..8219ffdd679d2 100644
--- 
a/llvm/test/CodeGen/D

[llvm-branch-commits] [mlir] [mlir][omp] Add omp.tile operation (PR #160292)

2025-09-24 Thread Tom Eccles via llvm-branch-commits

https://github.com/tblah edited https://github.com/llvm/llvm-project/pull/160292
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] [mlir][omp] Add omp.tile operation (PR #160292)

2025-09-24 Thread Tom Eccles via llvm-branch-commits

https://github.com/tblah commented:

Looks great. Just one question about the change to generic MLIR code.

https://github.com/llvm/llvm-project/pull/160292
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [LifetimeSafety] Introduce a liveness-based lifetime policy (PR #159991)

2025-09-24 Thread Utkarsh Saxena via llvm-branch-commits


@@ -138,7 +148,7 @@ class LifetimeSafetyAnalysis {
   std::unique_ptr Factory;
   std::unique_ptr FactMgr;
   std::unique_ptr LoanPropagation;
-  std::unique_ptr ExpiredLoans;
+  std::unique_ptr LiveOrigins;

usx95 wrote:

We cannot store these directly as we have a forward decl to these in `.h` and a 
full definition is only available in the implementation file :/ 

https://github.com/llvm/llvm-project/pull/159991
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [libunwind] release/21.x: [Mips] Fixed libunwind::Registers_mips_o32::jumpto to allow for load delay (#152942) (PR #160638)

2025-09-24 Thread via llvm-branch-commits

llvmbot wrote:




@llvm/pr-subscribers-libunwind

Author: None (llvmbot)


Changes

Backport a3d7c468bdc328f04da720088b2e542ef1f33ffc

Requested by: @brad0

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


1 Files Affected:

- (modified) libunwind/src/UnwindRegistersRestore.S (+5-2) 


``diff
diff --git a/libunwind/src/UnwindRegistersRestore.S 
b/libunwind/src/UnwindRegistersRestore.S
index 5e199188945df..1bcd205be260d 100644
--- a/libunwind/src/UnwindRegistersRestore.S
+++ b/libunwind/src/UnwindRegistersRestore.S
@@ -1044,9 +1044,10 @@ 
DEFINE_LIBUNWIND_FUNCTION(_ZN9libunwind18Registers_mips_o326jumptoEv)
   lw$27, (4 * 27)($4)
   lw$28, (4 * 28)($4)
   lw$29, (4 * 29)($4)
-  lw$30, (4 * 30)($4)
   // load new pc into ra
   lw$31, (4 * 32)($4)
+  // MIPS 1 has load delay slot. Ensure lw $31 and jr are separated by an 
instruction.
+  lw$30, (4 * 30)($4)
   // jump to ra, load a0 in the delay slot
   jr$31
   lw$4, (4 * 4)($4)
@@ -1082,11 +1083,13 @@ 
DEFINE_LIBUNWIND_FUNCTION(_ZN9libunwind21Registers_mips_newabi6jumptoEv)
   ld$2, (8 * 2)($4)
   ld$3, (8 * 3)($4)
   // skip a0 for now
-  .irp 
i,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30
+  .irp i,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29
 ld $\i, (8 * \i)($4)
   .endr
   // load new pc into ra
   ld$31, (8 * 32)($4)
+  // MIPS 1 has load delay slot. Ensure lw $31 and jr are separated by an 
instruction.
+  ld$30, (8 * 30)($4)
   // jump to ra, load a0 in the delay slot
   jr$31
   ld$4, (8 * 4)($4)

``




https://github.com/llvm/llvm-project/pull/160638
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [libunwind] release/21.x: [Mips] Fixed libunwind::Registers_mips_o32::jumpto to allow for load delay (#152942) (PR #160638)

2025-09-24 Thread via llvm-branch-commits

https://github.com/llvmbot milestoned 
https://github.com/llvm/llvm-project/pull/160638
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] [llvm-remarkutil] Introduce filter command (PR #159784)

2025-09-24 Thread Florian Hahn via llvm-branch-commits


@@ -0,0 +1,84 @@
+//===- RemarkFilter.cpp 
---===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM 
Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===--===//
+//
+// Generic tool to filter remarks
+//
+//===--===//
+
+#include "RemarkUtilHelpers.h"
+#include "RemarkUtilRegistry.h"
+
+#include "llvm/Support/Error.h"
+#include "llvm/Support/Regex.h"
+
+using namespace llvm;
+using namespace remarks;
+using namespace llvm::remarkutil;
+
+namespace filter {
+
+static cl::SubCommand FilterSub("filter",
+"Filter remarks based on specified criteria.");
+
+INPUT_FORMAT_COMMAND_LINE_OPTIONS(FilterSub)
+OUTPUT_FORMAT_COMMAND_LINE_OPTIONS(FilterSub)
+INPUT_OUTPUT_COMMAND_LINE_OPTIONS(FilterSub)
+REMARK_FILTER_COMMAND_LINE_OPTIONS(FilterSub)
+
+REMARK_FILTER_SETUP_FUNC()
+
+static Error tryFilter() {
+  auto MaybeFilter = getRemarkFilters();
+  if (!MaybeFilter)
+return MaybeFilter.takeError();
+  Filters &Filter = *MaybeFilter;
+
+  auto MaybeBuf = getInputMemoryBuffer(InputFileName);
+  if (!MaybeBuf)
+return MaybeBuf.takeError();
+  auto MaybeParser = createRemarkParser(InputFormat, (*MaybeBuf)->getBuffer());
+  if (!MaybeParser)
+return MaybeParser.takeError();
+  auto &Parser = **MaybeParser;
+
+  Format SerializerFormat = OutputFormat;
+  if (SerializerFormat == Format::Auto) {
+SerializerFormat = Parser.ParserFormat;
+if (OutputFileName.empty() || OutputFileName == "-")
+  SerializerFormat = Format::YAML;
+  }
+
+  auto MaybeOF = getOutputFileForRemarks(OutputFileName, SerializerFormat);
+  if (!MaybeOF)
+return MaybeOF.takeError();
+  auto OF = std::move(*MaybeOF);
+
+  auto MaybeSerializer = createRemarkSerializer(SerializerFormat, OF->os());
+  if (!MaybeSerializer)
+return MaybeSerializer.takeError();
+  auto &Serializer = **MaybeSerializer;
+
+  auto MaybeRemark = Parser.next();
+  for (; MaybeRemark; MaybeRemark = Parser.next()) {
+Remark &Remark = **MaybeRemark;
+if (!Filter.filterRemark(Remark))
+  continue;
+Serializer.emit(Remark);
+  }

fhahn wrote:

Yeah that's OK, although this might be worth more thought in the future, to 
avoid duplicating the logic in every remarks tool

https://github.com/llvm/llvm-project/pull/159784
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] [llvm-remarkutil] Introduce filter command (PR #159784)

2025-09-24 Thread Florian Hahn via llvm-branch-commits

https://github.com/fhahn edited https://github.com/llvm/llvm-project/pull/159784
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] [mlir][omp] Add omp.tile operation (PR #160292)

2025-09-24 Thread Michael Kruse via llvm-branch-commits

https://github.com/Meinersbur edited 
https://github.com/llvm/llvm-project/pull/160292
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [mlir] [mlir][omp] Add omp.tile operation (PR #160292)

2025-09-24 Thread via llvm-branch-commits

llvmbot wrote:




@llvm/pr-subscribers-mlir-llvm

Author: Michael Kruse (Meinersbur)


Changes

Add the `omp.tile` loop transformations for the OpenMP dialect. Used for 
lowering a standalone `!$omp tile` in Flang.

The pretty operation printing format is currently inconcistent between 
`omp.canonical_loop`, `omp.unroll_heuristic`, and `omp.tile`. Open for 
suggestions what the concistent format should be.

PR Stack:
 * #160283
 * #159773
 * #160292 (this PR)
 * #160298

---

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


13 Files Affected:

- (modified) mlir/include/mlir/Dialect/OpenMP/OpenMPClauses.td (+29) 
- (modified) mlir/include/mlir/Dialect/OpenMP/OpenMPOpBase.td (+67-2) 
- (modified) mlir/include/mlir/Dialect/OpenMP/OpenMPOps.td (+25-38) 
- (modified) mlir/lib/Dialect/OpenMP/IR/OpenMPDialect.cpp (+154) 
- (modified) 
mlir/lib/Target/LLVMIR/Dialect/OpenMP/OpenMPToLLVMIRTranslation.cpp (+42) 
- (added) mlir/test/Dialect/OpenMP/cli-tile.mlir (+138) 
- (added) mlir/test/Dialect/OpenMP/invalid-tile.mlir (+119) 
- (added) mlir/test/Target/LLVMIR/openmp-cli-tile01.mlir (+101) 
- (added) mlir/test/Target/LLVMIR/openmp-cli-tile02.mlir (+190) 
- (modified) mlir/test/mlir-tblgen/op-format-invalid.td (+1-1) 
- (modified) mlir/tools/mlir-tblgen/AttrOrTypeFormatGen.cpp (+1) 
- (modified) mlir/tools/mlir-tblgen/FormatGen.cpp (+1-1) 
- (modified) mlir/tools/mlir-tblgen/OpFormatGen.cpp (+1) 


``diff
diff --git a/mlir/include/mlir/Dialect/OpenMP/OpenMPClauses.td 
b/mlir/include/mlir/Dialect/OpenMP/OpenMPClauses.td
index 1eda5e4bc1618..8e43c4284d078 100644
--- a/mlir/include/mlir/Dialect/OpenMP/OpenMPClauses.td
+++ b/mlir/include/mlir/Dialect/OpenMP/OpenMPClauses.td
@@ -995,6 +995,35 @@ class OpenMP_NumTeamsClauseSkip<
 
 def OpenMP_NumTeamsClause : OpenMP_NumTeamsClauseSkip<>;
 
+//===--===//
+//  V5.1: [10.1.2] `sizes` clause
+//===--===//
+
+class OpenMP_SizesClauseSkip<
+bit traits = false, bit arguments = false, bit assemblyFormat = false,
+bit description = false, bit extraClassDeclaration = false
+  > : OpenMP_Clause {
+  let arguments = (ins
+Variadic:$sizes
+  );
+
+  let optAssemblyFormat = [{
+`sizes` `(` $sizes `:` type($sizes) `)`
+  }];
+
+  let description = [{
+The `sizes` clauses defines the size of a grid over a multi-dimensional
+logical iteration space. This grid is used for loop transformations such as
+`tile` and `strip`. The size per dimension can be a variable, but only
+values that are not at least 2 make sense. It is not specified what happens
+when smaller values are used, but should still result in a loop nest that
+executes each logical iteration once.
+  }];
+}
+
+def OpenMP_SizesClause : OpenMP_SizesClauseSkip<>;
+
 
//===--===//
 // V5.2: [10.1.2] `num_threads` clause
 
//===--===//
diff --git a/mlir/include/mlir/Dialect/OpenMP/OpenMPOpBase.td 
b/mlir/include/mlir/Dialect/OpenMP/OpenMPOpBase.td
index bbcfb87fa03c6..5ad4e4b5b61d1 100644
--- a/mlir/include/mlir/Dialect/OpenMP/OpenMPOpBase.td
+++ b/mlir/include/mlir/Dialect/OpenMP/OpenMPOpBase.td
@@ -38,6 +38,44 @@ def OpenMP_MapBoundsType : OpenMP_Type<"MapBounds", 
"map_bounds_ty"> {
   let summary = "Type for representing omp map clause bounds information";
 }
 
+//===-===//
+// 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
+   a result of that transformation. The CLI is

[llvm-branch-commits] [flang] [llvm] [openmp] [Flang] Add standalone tile support (PR #160298)

2025-09-24 Thread Michael Kruse via llvm-branch-commits

https://github.com/Meinersbur updated 
https://github.com/llvm/llvm-project/pull/160298

>From bfe9c6b642ebc01f113dbf0a574e424e83f7162a Mon Sep 17 00:00:00 2001
From: Michael Kruse 
Date: Tue, 23 Sep 2025 15:33:52 +0200
Subject: [PATCH 1/3] [flang] Add standalone tile support

---
 flang/lib/Lower/OpenMP/ClauseProcessor.cpp|  13 +
 flang/lib/Lower/OpenMP/ClauseProcessor.h  |   2 +
 flang/lib/Lower/OpenMP/OpenMP.cpp | 360 --
 flang/lib/Lower/OpenMP/Utils.cpp  |  23 +-
 flang/lib/Lower/OpenMP/Utils.h|   7 +
 .../lib/Semantics/check-directive-structure.h |   7 +-
 flang/lib/Semantics/check-omp-structure.cpp   |   8 +-
 flang/lib/Semantics/resolve-directives.cpp|  16 +-
 flang/test/Lower/OpenMP/tile01.f90|  58 +++
 flang/test/Lower/OpenMP/tile02.f90|  88 +
 .../loop-transformation-construct02.f90   |   5 +-
 flang/test/Parser/OpenMP/tile-fail.f90|  32 ++
 flang/test/Parser/OpenMP/tile.f90 |  15 +-
 flang/test/Semantics/OpenMP/tile01.f90|  26 ++
 flang/test/Semantics/OpenMP/tile02.f90|  15 +
 flang/test/Semantics/OpenMP/tile03.f90|  15 +
 flang/test/Semantics/OpenMP/tile04.f90|  38 ++
 flang/test/Semantics/OpenMP/tile05.f90|  14 +
 flang/test/Semantics/OpenMP/tile06.f90|  44 +++
 flang/test/Semantics/OpenMP/tile07.f90|  35 ++
 flang/test/Semantics/OpenMP/tile08.f90|  15 +
 llvm/include/llvm/Frontend/OpenMP/OMP.td  |   3 +
 openmp/runtime/test/transform/tile/intfor.f90 |  31 ++
 .../runtime/test/transform/tile/intfor_2d.f90 |  53 +++
 .../transform/tile/intfor_2d_varsizes.F90 |  60 +++
 25 files changed, 841 insertions(+), 142 deletions(-)
 create mode 100644 flang/test/Lower/OpenMP/tile01.f90
 create mode 100644 flang/test/Lower/OpenMP/tile02.f90
 create mode 100644 flang/test/Parser/OpenMP/tile-fail.f90
 create mode 100644 flang/test/Semantics/OpenMP/tile01.f90
 create mode 100644 flang/test/Semantics/OpenMP/tile02.f90
 create mode 100644 flang/test/Semantics/OpenMP/tile03.f90
 create mode 100644 flang/test/Semantics/OpenMP/tile04.f90
 create mode 100644 flang/test/Semantics/OpenMP/tile05.f90
 create mode 100644 flang/test/Semantics/OpenMP/tile06.f90
 create mode 100644 flang/test/Semantics/OpenMP/tile07.f90
 create mode 100644 flang/test/Semantics/OpenMP/tile08.f90
 create mode 100644 openmp/runtime/test/transform/tile/intfor.f90
 create mode 100644 openmp/runtime/test/transform/tile/intfor_2d.f90
 create mode 100644 openmp/runtime/test/transform/tile/intfor_2d_varsizes.F90

diff --git a/flang/lib/Lower/OpenMP/ClauseProcessor.cpp 
b/flang/lib/Lower/OpenMP/ClauseProcessor.cpp
index a96884f5680ba..55eda7e3404c1 100644
--- a/flang/lib/Lower/OpenMP/ClauseProcessor.cpp
+++ b/flang/lib/Lower/OpenMP/ClauseProcessor.cpp
@@ -431,6 +431,19 @@ bool ClauseProcessor::processNumTasks(
   return false;
 }
 
+bool ClauseProcessor::processSizes(StatementContext &stmtCtx,
+   mlir::omp::SizesClauseOps &result) const {
+  if (auto *clause = findUniqueClause()) {
+result.sizes.reserve(clause->v.size());
+for (const ExprTy &vv : clause->v)
+  result.sizes.push_back(fir::getBase(converter.genExprValue(vv, 
stmtCtx)));
+
+return true;
+  }
+
+  return false;
+}
+
 bool ClauseProcessor::processNumTeams(
 lower::StatementContext &stmtCtx,
 mlir::omp::NumTeamsClauseOps &result) const {
diff --git a/flang/lib/Lower/OpenMP/ClauseProcessor.h 
b/flang/lib/Lower/OpenMP/ClauseProcessor.h
index 324ea3c1047a5..9e352fa574a97 100644
--- a/flang/lib/Lower/OpenMP/ClauseProcessor.h
+++ b/flang/lib/Lower/OpenMP/ClauseProcessor.h
@@ -66,6 +66,8 @@ class ClauseProcessor {
   mlir::omp::LoopRelatedClauseOps &loopResult,
   mlir::omp::CollapseClauseOps &collapseResult,
   llvm::SmallVectorImpl &iv) const;
+  bool processSizes(StatementContext &stmtCtx,
+mlir::omp::SizesClauseOps &result) const;
   bool processDevice(lower::StatementContext &stmtCtx,
  mlir::omp::DeviceClauseOps &result) const;
   bool processDeviceType(mlir::omp::DeviceTypeClauseOps &result) const;
diff --git a/flang/lib/Lower/OpenMP/OpenMP.cpp 
b/flang/lib/Lower/OpenMP/OpenMP.cpp
index 5681be664d450..7812d9fe00be2 100644
--- a/flang/lib/Lower/OpenMP/OpenMP.cpp
+++ b/flang/lib/Lower/OpenMP/OpenMP.cpp
@@ -1984,125 +1984,241 @@ genLoopOp(lower::AbstractConverter &converter, 
lower::SymMap &symTable,
   return loopOp;
 }
 
-static mlir::omp::CanonicalLoopOp
-genCanonicalLoopOp(lower::AbstractConverter &converter, lower::SymMap 
&symTable,
-   semantics::SemanticsContext &semaCtx,
-   lower::pft::Evaluation &eval, mlir::Location loc,
-   const ConstructQueue &queue,
-   ConstructQueue::const_iterator item,
-   llvm::ArrayRef ivs,
-   llvm::omp::Directive directive)

[llvm-branch-commits] [mlir] [mlir][omp] Add omp.tile operation (PR #160292)

2025-09-24 Thread Michael Kruse via llvm-branch-commits

https://github.com/Meinersbur updated 
https://github.com/llvm/llvm-project/pull/160292

>From ff4eccb41e2973e1179734dd455f1e797e89d9be Mon Sep 17 00:00:00 2001
From: Michael Kruse 
Date: Tue, 23 Sep 2025 14:45:45 +0200
Subject: [PATCH] Add omp.tile operation

---
 .../mlir/Dialect/OpenMP/OpenMPClauses.td  |  29 ++
 .../mlir/Dialect/OpenMP/OpenMPOpBase.td   |  69 +++-
 mlir/include/mlir/Dialect/OpenMP/OpenMPOps.td |  63 ++-
 mlir/lib/Dialect/OpenMP/IR/OpenMPDialect.cpp  | 387 +++---
 .../OpenMP/OpenMPToLLVMIRTranslation.cpp  |  42 ++
 .../Dialect/OpenMP/cli-canonical_loop.mlir| 127 --
 mlir/test/Dialect/OpenMP/cli-tile.mlir| 138 +++
 .../Dialect/OpenMP/cli-unroll-heuristic.mlir  |  28 +-
 mlir/test/Dialect/OpenMP/invalid-tile.mlir| 119 ++
 .../test/Target/LLVMIR/openmp-cli-tile01.mlir | 101 +
 .../test/Target/LLVMIR/openmp-cli-tile02.mlir | 190 +
 mlir/test/mlir-tblgen/op-format-invalid.td|   2 +-
 .../tools/mlir-tblgen/AttrOrTypeFormatGen.cpp |   1 +
 mlir/tools/mlir-tblgen/FormatGen.cpp  |   2 +-
 mlir/tools/mlir-tblgen/OpFormatGen.cpp|   1 +
 15 files changed, 1157 insertions(+), 142 deletions(-)
 create mode 100644 mlir/test/Dialect/OpenMP/cli-tile.mlir
 create mode 100644 mlir/test/Dialect/OpenMP/invalid-tile.mlir
 create mode 100644 mlir/test/Target/LLVMIR/openmp-cli-tile01.mlir
 create mode 100644 mlir/test/Target/LLVMIR/openmp-cli-tile02.mlir

diff --git a/mlir/include/mlir/Dialect/OpenMP/OpenMPClauses.td 
b/mlir/include/mlir/Dialect/OpenMP/OpenMPClauses.td
index 1eda5e4bc1618..8e43c4284d078 100644
--- a/mlir/include/mlir/Dialect/OpenMP/OpenMPClauses.td
+++ b/mlir/include/mlir/Dialect/OpenMP/OpenMPClauses.td
@@ -995,6 +995,35 @@ class OpenMP_NumTeamsClauseSkip<
 
 def OpenMP_NumTeamsClause : OpenMP_NumTeamsClauseSkip<>;
 
+//===--===//
+//  V5.1: [10.1.2] `sizes` clause
+//===--===//
+
+class OpenMP_SizesClauseSkip<
+bit traits = false, bit arguments = false, bit assemblyFormat = false,
+bit description = false, bit extraClassDeclaration = false
+  > : OpenMP_Clause {
+  let arguments = (ins
+Variadic:$sizes
+  );
+
+  let optAssemblyFormat = [{
+`sizes` `(` $sizes `:` type($sizes) `)`
+  }];
+
+  let description = [{
+The `sizes` clauses defines the size of a grid over a multi-dimensional
+logical iteration space. This grid is used for loop transformations such as
+`tile` and `strip`. The size per dimension can be a variable, but only
+values that are not at least 2 make sense. It is not specified what happens
+when smaller values are used, but should still result in a loop nest that
+executes each logical iteration once.
+  }];
+}
+
+def OpenMP_SizesClause : OpenMP_SizesClauseSkip<>;
+
 
//===--===//
 // V5.2: [10.1.2] `num_threads` clause
 
//===--===//
diff --git a/mlir/include/mlir/Dialect/OpenMP/OpenMPOpBase.td 
b/mlir/include/mlir/Dialect/OpenMP/OpenMPOpBase.td
index bbcfb87fa03c6..5ad4e4b5b61d1 100644
--- a/mlir/include/mlir/Dialect/OpenMP/OpenMPOpBase.td
+++ b/mlir/include/mlir/Dialect/OpenMP/OpenMPOpBase.td
@@ -38,6 +38,44 @@ def OpenMP_MapBoundsType : OpenMP_Type<"MapBounds", 
"map_bounds_ty"> {
   let summary = "Type for representing omp map clause bounds information";
 }
 
+//===-===//
+// 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
+   a result of that transformation. The CLI is the "generatee" and the
+   operatio

[llvm-branch-commits] [clang] [analyzer] Revert #115918, so empty base class optimization works again (#157480) (PR #160450)

2025-09-24 Thread Gábor Horváth via llvm-branch-commits

https://github.com/Xazax-hun approved this pull request.


https://github.com/llvm/llvm-project/pull/160450
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [clang] [clang] simplify placeholder type deduction for constant template parameters (PR #160439)

2025-09-24 Thread Matheus Izvekov via llvm-branch-commits

https://github.com/mizvekov created 
https://github.com/llvm/llvm-project/pull/160439

This makes the deduction for dependent types operate in more similar ways to 
the non-dependent one, such as when matching template template parameters, 
making errors in those generate similar diagnostics to the non-dependent ones. 
This also removes some superfluous implicit casts, simplifying the resulting 
AST a little bit.

>From 87c83594790c3a5f0d9188e02a12c4b21eaa53fc Mon Sep 17 00:00:00 2001
From: Matheus Izvekov 
Date: Wed, 24 Sep 2025 00:21:01 -0300
Subject: [PATCH] [clang] simplify placeholder type deduction for constant
 template parameters

This makes the deduction for dependent types operate in more similar ways
to the non-dependent one, such as when matching template template parameters,
making errors in those generate similar diagnostics to the non-dependent ones.
This also removes some superfluous implicit casts, simplifying the resulting
AST a little bit.
---
 clang/docs/ReleaseNotes.rst   |  3 +-
 clang/lib/Sema/SemaTemplate.cpp   | 68 +--
 clang/lib/Sema/SemaTemplateDeduction.cpp  | 32 -
 .../SemaTemplate/temp_arg_template_p0522.cpp  | 10 +--
 4 files changed, 52 insertions(+), 61 deletions(-)

diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index 70c82b090107a..1932135ceed1b 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -292,7 +292,8 @@ Improvements to Clang's diagnostics
   "format specifies type 'unsigned int' but the argument has type 'int', which 
differs in signedness [-Wformat-signedness]"
   "signedness of format specifier 'u' is incompatible with 'c' 
[-Wformat-signedness]"
   and the API-visible diagnostic id will be appropriate.
-
+- Clang now produces better diagnostics for template template parameter 
matching
+  involving 'auto' template parameters.
 - Fixed false positives in ``-Waddress-of-packed-member`` diagnostics when
   potential misaligned members get processed before they can get discarded.
   (#GH144729)
diff --git a/clang/lib/Sema/SemaTemplate.cpp b/clang/lib/Sema/SemaTemplate.cpp
index f051a246f954f..5a48ba0c344b7 100644
--- a/clang/lib/Sema/SemaTemplate.cpp
+++ b/clang/lib/Sema/SemaTemplate.cpp
@@ -7068,22 +7068,8 @@ ExprResult Sema::CheckTemplateArgument(NamedDecl *Param, 
QualType ParamType,
 
   // If the parameter type somehow involves auto, deduce the type now.
   DeducedType *DeducedT = ParamType->getContainedDeducedType();
-  if (getLangOpts().CPlusPlus17 && DeducedT && !DeducedT->isDeduced()) {
-// During template argument deduction, we allow 'decltype(auto)' to
-// match an arbitrary dependent argument.
-// FIXME: The language rules don't say what happens in this case.
-// FIXME: We get an opaque dependent type out of decltype(auto) if the
-// expression is merely instantiation-dependent; is this enough?
-if (DeductionArg->isTypeDependent()) {
-  auto *AT = dyn_cast(DeducedT);
-  if (AT && AT->isDecltypeAuto()) {
-SugaredConverted = TemplateArgument(Arg, /*IsCanonical=*/false);
-CanonicalConverted = TemplateArgument(
-Context.getCanonicalTemplateArgument(SugaredConverted));
-return Arg;
-  }
-}
-
+  bool IsDeduced = DeducedT && !DeducedT->isDeduced();
+  if (IsDeduced) {
 // When checking a deduced template argument, deduce from its type even if
 // the type is dependent, in order to check the types of non-type template
 // arguments line up properly in partial ordering.
@@ -7112,17 +7098,21 @@ ExprResult Sema::CheckTemplateArgument(NamedDecl 
*Param, QualType ParamType,
  // along with the other associated constraints after
  // checking the template argument list.
  /*IgnoreConstraints=*/true);
-  if (Result == TemplateDeductionResult::AlreadyDiagnosed) {
-return ExprError();
-  } else if (Result != TemplateDeductionResult::Success) {
-if (const auto *NTTP = dyn_cast(Param)) {
-  Diag(Arg->getExprLoc(),
-   diag::err_non_type_template_parm_type_deduction_failure)
-  << Param->getDeclName() << NTTP->getType() << Arg->getType()
-  << Arg->getSourceRange();
+  if (Result != TemplateDeductionResult::Success) {
+ParamType = TSI->getType();
+if (StrictCheck || !DeductionArg->isTypeDependent()) {
+  if (Result == TemplateDeductionResult::AlreadyDiagnosed)
+return ExprError();
+  if (const auto *NTTP = dyn_cast(Param))
+Diag(Arg->getExprLoc(),
+ diag::err_non_type_template_parm_type_deduction_failure)
+<< Param->getDeclName() << NTTP->getType() << Arg->getType()
+<< Arg->getSourceRange();
+  NoteTemplateParameterLocation(*Param);
+  return ExprError();
 }
-NoteTemplateParameterLocation(*Param);
- 

[llvm-branch-commits] [flang] [llvm] [mlir] [Flang][OpenMP][MLIR] Initial declare target to for variables implementation (PR #119589)

2025-09-24 Thread Akash Banerjee via llvm-branch-commits


@@ -3664,6 +3690,30 @@ struct MapInfoData : MapInfosTy {
 MapInfosTy::append(CurInfo);
   }
 };
+
+enum class TargetDirective : uint32_t {
+  None = 0,
+  Target = 1,
+  TargetData = 2,
+  TargetEnterData = 3,
+  TargetExitData = 4,
+  TargetUpdate = 5
+};

TIFitis wrote:

Nit: Rename to something like `TargetDirectiveTy` or `TargetDirectiveEnumTy` 
for clarity.

Also, should this be enclosed in a namespace?

https://github.com/llvm/llvm-project/pull/119589
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [flang] [flang][OpenMP] Use OmpDirectiveSpecification in DECLARE_TARGET (PR #160573)

2025-09-24 Thread via llvm-branch-commits

llvmbot wrote:




@llvm/pr-subscribers-flang-fir-hlfir

Author: Krzysztof Parzyszek (kparzysz)


Changes



---

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


16 Files Affected:

- (modified) flang/include/flang/Parser/openmp-utils.h (-2) 
- (modified) flang/include/flang/Parser/parse-tree.h (+8-2) 
- (modified) flang/lib/Lower/OpenMP/OpenMP.cpp (+6-8) 
- (modified) flang/lib/Parser/openmp-parsers.cpp (+3-15) 
- (modified) flang/lib/Parser/unparse.cpp (+2-2) 
- (modified) flang/lib/Semantics/check-omp-structure.cpp (+124-121) 
- (modified) flang/lib/Semantics/check-omp-structure.h (-3) 
- (modified) flang/lib/Semantics/resolve-directives.cpp (+11-16) 
- (modified) flang/lib/Semantics/resolve-names.cpp (+34-43) 
- (modified) flang/test/Parser/OpenMP/declare-target-indirect-tree.f90 (+16-12) 
- (modified) flang/test/Parser/OpenMP/declare-target-to-clause.f90 (+8-6) 
- (modified) flang/test/Parser/OpenMP/declare_target-device_type.f90 (+93-15) 
- (modified) flang/test/Parser/OpenMP/enter-automap-modifier.f90 (+7-4) 
- (modified) flang/test/Parser/OpenMP/openmp6-directive-spellings.f90 (+5-4) 
- (modified) flang/test/Semantics/OpenMP/blank-common-block.f90 (+1) 
- (modified) 
flang/test/Semantics/OpenMP/declare-target-function-name-with-symbols.f90 
(+1-1) 


``diff
diff --git a/flang/include/flang/Parser/openmp-utils.h 
b/flang/include/flang/Parser/openmp-utils.h
index 4b8fe6a5b49f0..bf54f970a7d3a 100644
--- a/flang/include/flang/Parser/openmp-utils.h
+++ b/flang/include/flang/Parser/openmp-utils.h
@@ -41,7 +41,6 @@ struct ConstructId {
 MAKE_CONSTR_ID(OpenMPDeclarativeAllocate, D::OMPD_allocate);
 MAKE_CONSTR_ID(OpenMPDeclarativeAssumes, D::OMPD_assumes);
 MAKE_CONSTR_ID(OpenMPDeclareReductionConstruct, D::OMPD_declare_reduction);
-MAKE_CONSTR_ID(OpenMPDeclareTargetConstruct, D::OMPD_declare_target);
 MAKE_CONSTR_ID(OpenMPExecutableAllocate, D::OMPD_allocate);
 MAKE_CONSTR_ID(OpenMPRequiresConstruct, D::OMPD_requires);
 
@@ -97,7 +96,6 @@ struct DirectiveNameScope {
   } else if constexpr (std::is_same_v ||
   std::is_same_v ||
   std::is_same_v ||
-  std::is_same_v ||
   std::is_same_v ||
   std::is_same_v) {
 return MakeName(std::get(x.t).source, ConstructId::id);
diff --git a/flang/include/flang/Parser/parse-tree.h 
b/flang/include/flang/Parser/parse-tree.h
index be30a95763208..e7593d9875097 100644
--- a/flang/include/flang/Parser/parse-tree.h
+++ b/flang/include/flang/Parser/parse-tree.h
@@ -4961,10 +4961,16 @@ struct OmpDeclareTargetSpecifier {
   std::variant u;
 };
 
+// Ref: [4.5:110-113], [5.0:180-185], [5.1:210-216], [5.2:206-207],
+//  [6.0:346-348]
+//
+// declare-target-directive ->  // since 4.5
+//DECLARE_TARGET[(extended-list)] |
+//DECLARE_TARGET clause-list
 struct OpenMPDeclareTargetConstruct {
-  TUPLE_CLASS_BOILERPLATE(OpenMPDeclareTargetConstruct);
+  WRAPPER_CLASS_BOILERPLATE(
+  OpenMPDeclareTargetConstruct, OmpDirectiveSpecification);
   CharBlock source;
-  std::tuple t;
 };
 
 // OMP v5.2: 5.8.8
diff --git a/flang/lib/Lower/OpenMP/OpenMP.cpp 
b/flang/lib/Lower/OpenMP/OpenMP.cpp
index d2e865b3e1d0c..1cb3335abbd06 100644
--- a/flang/lib/Lower/OpenMP/OpenMP.cpp
+++ b/flang/lib/Lower/OpenMP/OpenMP.cpp
@@ -761,19 +761,17 @@ static void promoteNonCPtrUseDevicePtrArgsToUseDeviceAddr(
 static void getDeclareTargetInfo(
 lower::AbstractConverter &converter, semantics::SemanticsContext &semaCtx,
 lower::pft::Evaluation &eval,
-const parser::OpenMPDeclareTargetConstruct &declareTargetConstruct,
+const parser::OpenMPDeclareTargetConstruct &construct,
 mlir::omp::DeclareTargetOperands &clauseOps,
 llvm::SmallVectorImpl &symbolAndClause) {
-  const auto &spec =
-  std::get(declareTargetConstruct.t);
-  if (const auto *objectList{parser::Unwrap(spec.u)}) {
-ObjectList objects{makeObjects(*objectList, semaCtx)};
+
+  if (!construct.v.Arguments().v.empty()) {
+ObjectList objects{makeObjects(construct.v.Arguments(), semaCtx)};
 // Case: declare target(func, var1, var2)
 gatherFuncAndVarSyms(objects, mlir::omp::DeclareTargetCaptureClause::to,
  symbolAndClause, /*automap=*/false);
-  } else if (const auto *clauseList{
- parser::Unwrap(spec.u)}) {
-List clauses = makeClauses(*clauseList, semaCtx);
+  } else {
+List clauses = makeClauses(construct.v.Clauses(), semaCtx);
 if (clauses.empty()) {
   Fortran::lower::pft::FunctionLikeUnit *owningProc =
   eval.getOwningProcedure();
diff --git a/flang/lib/Parser/openmp-parsers.cpp 
b/flang/lib/Parser/openmp-parsers.cpp
index 0085576292ff5..bd080386c0aea 100644
--- a/flang/lib/Parser/openmp-parsers.cpp
+++ b/flang/lib/Parser/openmp-parsers.cpp
@@ -1773,23 +1773,11 @@ 
TYPE_PARSER(sourced(construct(
 IsDirective(llvm::omp::Directive::OMPD_declare_reduction)) >=
 Parser{}))

[llvm-branch-commits] [flang] [flang][OpenMP] Use OmpDirectiveSpecification in DECLARE_TARGET (PR #160573)

2025-09-24 Thread via llvm-branch-commits

llvmbot wrote:



@llvm/pr-subscribers-flang-semantics

@llvm/pr-subscribers-flang-parser

Author: Krzysztof Parzyszek (kparzysz)


Changes



---

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


16 Files Affected:

- (modified) flang/include/flang/Parser/openmp-utils.h (-2) 
- (modified) flang/include/flang/Parser/parse-tree.h (+8-2) 
- (modified) flang/lib/Lower/OpenMP/OpenMP.cpp (+6-8) 
- (modified) flang/lib/Parser/openmp-parsers.cpp (+3-15) 
- (modified) flang/lib/Parser/unparse.cpp (+2-2) 
- (modified) flang/lib/Semantics/check-omp-structure.cpp (+124-121) 
- (modified) flang/lib/Semantics/check-omp-structure.h (-3) 
- (modified) flang/lib/Semantics/resolve-directives.cpp (+11-16) 
- (modified) flang/lib/Semantics/resolve-names.cpp (+34-43) 
- (modified) flang/test/Parser/OpenMP/declare-target-indirect-tree.f90 (+16-12) 
- (modified) flang/test/Parser/OpenMP/declare-target-to-clause.f90 (+8-6) 
- (modified) flang/test/Parser/OpenMP/declare_target-device_type.f90 (+93-15) 
- (modified) flang/test/Parser/OpenMP/enter-automap-modifier.f90 (+7-4) 
- (modified) flang/test/Parser/OpenMP/openmp6-directive-spellings.f90 (+5-4) 
- (modified) flang/test/Semantics/OpenMP/blank-common-block.f90 (+1) 
- (modified) 
flang/test/Semantics/OpenMP/declare-target-function-name-with-symbols.f90 
(+1-1) 


``diff
diff --git a/flang/include/flang/Parser/openmp-utils.h 
b/flang/include/flang/Parser/openmp-utils.h
index 4b8fe6a5b49f0..bf54f970a7d3a 100644
--- a/flang/include/flang/Parser/openmp-utils.h
+++ b/flang/include/flang/Parser/openmp-utils.h
@@ -41,7 +41,6 @@ struct ConstructId {
 MAKE_CONSTR_ID(OpenMPDeclarativeAllocate, D::OMPD_allocate);
 MAKE_CONSTR_ID(OpenMPDeclarativeAssumes, D::OMPD_assumes);
 MAKE_CONSTR_ID(OpenMPDeclareReductionConstruct, D::OMPD_declare_reduction);
-MAKE_CONSTR_ID(OpenMPDeclareTargetConstruct, D::OMPD_declare_target);
 MAKE_CONSTR_ID(OpenMPExecutableAllocate, D::OMPD_allocate);
 MAKE_CONSTR_ID(OpenMPRequiresConstruct, D::OMPD_requires);
 
@@ -97,7 +96,6 @@ struct DirectiveNameScope {
   } else if constexpr (std::is_same_v ||
   std::is_same_v ||
   std::is_same_v ||
-  std::is_same_v ||
   std::is_same_v ||
   std::is_same_v) {
 return MakeName(std::get(x.t).source, ConstructId::id);
diff --git a/flang/include/flang/Parser/parse-tree.h 
b/flang/include/flang/Parser/parse-tree.h
index be30a95763208..e7593d9875097 100644
--- a/flang/include/flang/Parser/parse-tree.h
+++ b/flang/include/flang/Parser/parse-tree.h
@@ -4961,10 +4961,16 @@ struct OmpDeclareTargetSpecifier {
   std::variant u;
 };
 
+// Ref: [4.5:110-113], [5.0:180-185], [5.1:210-216], [5.2:206-207],
+//  [6.0:346-348]
+//
+// declare-target-directive ->  // since 4.5
+//DECLARE_TARGET[(extended-list)] |
+//DECLARE_TARGET clause-list
 struct OpenMPDeclareTargetConstruct {
-  TUPLE_CLASS_BOILERPLATE(OpenMPDeclareTargetConstruct);
+  WRAPPER_CLASS_BOILERPLATE(
+  OpenMPDeclareTargetConstruct, OmpDirectiveSpecification);
   CharBlock source;
-  std::tuple t;
 };
 
 // OMP v5.2: 5.8.8
diff --git a/flang/lib/Lower/OpenMP/OpenMP.cpp 
b/flang/lib/Lower/OpenMP/OpenMP.cpp
index d2e865b3e1d0c..1cb3335abbd06 100644
--- a/flang/lib/Lower/OpenMP/OpenMP.cpp
+++ b/flang/lib/Lower/OpenMP/OpenMP.cpp
@@ -761,19 +761,17 @@ static void promoteNonCPtrUseDevicePtrArgsToUseDeviceAddr(
 static void getDeclareTargetInfo(
 lower::AbstractConverter &converter, semantics::SemanticsContext &semaCtx,
 lower::pft::Evaluation &eval,
-const parser::OpenMPDeclareTargetConstruct &declareTargetConstruct,
+const parser::OpenMPDeclareTargetConstruct &construct,
 mlir::omp::DeclareTargetOperands &clauseOps,
 llvm::SmallVectorImpl &symbolAndClause) {
-  const auto &spec =
-  std::get(declareTargetConstruct.t);
-  if (const auto *objectList{parser::Unwrap(spec.u)}) {
-ObjectList objects{makeObjects(*objectList, semaCtx)};
+
+  if (!construct.v.Arguments().v.empty()) {
+ObjectList objects{makeObjects(construct.v.Arguments(), semaCtx)};
 // Case: declare target(func, var1, var2)
 gatherFuncAndVarSyms(objects, mlir::omp::DeclareTargetCaptureClause::to,
  symbolAndClause, /*automap=*/false);
-  } else if (const auto *clauseList{
- parser::Unwrap(spec.u)}) {
-List clauses = makeClauses(*clauseList, semaCtx);
+  } else {
+List clauses = makeClauses(construct.v.Clauses(), semaCtx);
 if (clauses.empty()) {
   Fortran::lower::pft::FunctionLikeUnit *owningProc =
   eval.getOwningProcedure();
diff --git a/flang/lib/Parser/openmp-parsers.cpp 
b/flang/lib/Parser/openmp-parsers.cpp
index 0085576292ff5..bd080386c0aea 100644
--- a/flang/lib/Parser/openmp-parsers.cpp
+++ b/flang/lib/Parser/openmp-parsers.cpp
@@ -1773,23 +1773,11 @@ 
TYPE_PARSER(sourced(construct(
 IsDirective(llvm::omp::Directive::OMPD_decl

[llvm-branch-commits] [flang] [llvm] [mlir] [Flang][OpenMP][MLIR] Initial declare target to for variables implementation (PR #119589)

2025-09-24 Thread Akash Banerjee via llvm-branch-commits


@@ -275,9 +275,21 @@ class MapInfoFinalizationPass
   return mapTypeFlag;
 
 mapFlags flags = mapFlags::OMP_MAP_TO |
- (mapFlags(mapTypeFlag) &
-  (mapFlags::OMP_MAP_IMPLICIT | mapFlags::OMP_MAP_CLOSE |
-   mapFlags::OMP_MAP_ALWAYS));
+ (mapFlags(mapTypeFlag) & mapFlags::OMP_MAP_IMPLICIT);
+
+// Descriptors for objects will always be copied. This is because the
+// descriptor can be rematerialized by the compiler, and so the address
+// of the descriptor for a given object at one place in the code may
+// differ from that address in another place. The contents of the
+// descriptor (the base address in particular) will remain unchanged
+// though.
+// TODO/FIXME: We currently cannot have MAP_CLOSE and MAP_ALWAYS on

TIFitis wrote:

This TODO/FIXME reads to me like a TODO for the Flang semantics/ MLIR op 
verifier? Or am I missing something?

https://github.com/llvm/llvm-project/pull/119589
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [flang] [llvm] [mlir] [Flang][OpenMP][MLIR] Initial declare target to for variables implementation (PR #119589)

2025-09-24 Thread Akash Banerjee via llvm-branch-commits


@@ -0,0 +1,35 @@
+// RUN: mlir-translate -mlir-to-llvmir %s | FileCheck %s
+
+// This tests the replacement of operations for `declare target to` with the
+// generated `declare target to` global variable inside of target op regions 
when
+// lowering to IR for device. Unfortunately, as the host file is not passed as 
a
+// module attribute, we miss out on the metadata and entry info.
+
+module attributes {llvm.target_triple = "amdgcn-amd-amdhsa", omp.is_gpu = 
true, omp.is_target_device = true} {
+  // CHECK-DAG: @_QMtest_0Ezii = global [11 x float] zeroinitializer
+  llvm.mlir.global external @_QMtest_0Ezii() {addr_space = 0 : i32, 
omp.declare_target = #omp.declaretarget} : !llvm.array<11 x f32> {
+%0 = llvm.mlir.zero : !llvm.array<11 x f32>
+llvm.return %0 : !llvm.array<11 x f32>
+  }
+
+  // CHECK-DAG: define weak_odr protected amdgpu_kernel void @{{.*}}(ptr 
%{{.*}}) {{.*}} {

TIFitis wrote:

Nit: Should this be a `CHECK-LABEL` followed by `CHECK-DAGs`?

https://github.com/llvm/llvm-project/pull/119589
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [flang] [llvm] [mlir] [Flang][OpenMP][MLIR] Initial declare target to for variables implementation (PR #119589)

2025-09-24 Thread Akash Banerjee via llvm-branch-commits


@@ -0,0 +1,30 @@
+! Test `declare target to` interaction with an allocatable with a non-default

TIFitis wrote:

Nit: The `to` clause doesn't appear in the test.

https://github.com/llvm/llvm-project/pull/119589
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [flang] [llvm] [mlir] [Flang][OpenMP][MLIR] Initial declare target to for variables implementation (PR #119589)

2025-09-24 Thread Akash Banerjee via llvm-branch-commits

https://github.com/TIFitis commented:

LGTM overall. I've added some nits below.

https://github.com/llvm/llvm-project/pull/119589
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [flang] [llvm] [mlir] [Flang][OpenMP][MLIR] Initial declare target to for variables implementation (PR #119589)

2025-09-24 Thread Akash Banerjee via llvm-branch-commits


@@ -0,0 +1,44 @@
+! Test that checks an allocatable array can be marked `declare target to` and
+! functions without issue.
+! REQUIRES: flang, amdgpu
+
+! RUN: %libomptarget-compile-fortran-run-and-check-generic
+module test
+implicit none
+integer, allocatable, dimension(:) :: alloca_arr
+!$omp declare target(alloca_arr)
+  end module test
+
+  program main
+use test
+implicit none
+integer :: cycle, i
+
+allocate(alloca_arr(10))
+
+do i = 1, 10
+alloca_arr(i) = 0
+end do
+
+!$omp target data map(to:alloca_arr)
+
+  do cycle = 1, 2
+
+!$omp target
+do i = 1, 10
+alloca_arr(i) = alloca_arr(i) + i
+end do
+!$omp end target
+
+! NOTE: Technically doesn't affect the results, but there is a
+! regression case that'll cause a runtime crash if this is
+! invoked more than once, so this checks for that.
+!$omp target update from(alloca_arr)

TIFitis wrote:

Nit: Indentation seems off.

https://github.com/llvm/llvm-project/pull/119589
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [llvm] Greedy: Merge VirtRegMap queries into one use (NFC) (PR #160485)

2025-09-24 Thread via llvm-branch-commits

llvmbot wrote:



@llvm/pr-subscribers-backend-systemz

@llvm/pr-subscribers-backend-x86

Author: Matt Arsenault (arsenm)


Changes



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


1 Files Affected:

- (modified) llvm/lib/CodeGen/RegAllocGreedy.cpp (+3-2) 


``diff
diff --git a/llvm/lib/CodeGen/RegAllocGreedy.cpp 
b/llvm/lib/CodeGen/RegAllocGreedy.cpp
index dc23ab3ce9d2b..6957548ac6c7a 100644
--- a/llvm/lib/CodeGen/RegAllocGreedy.cpp
+++ b/llvm/lib/CodeGen/RegAllocGreedy.cpp
@@ -2502,8 +2502,10 @@ void RAGreedy::tryHintRecoloring(const LiveInterval 
&VirtReg) {
   do {
 Reg = RecoloringCandidates.pop_back_val();
 
+MCRegister CurrPhys = VRM->getPhys(Reg);
+
 // This may be a skipped register.
-if (!VRM->hasPhys(Reg)) {
+if (!CurrPhys) {
   assert(!shouldAllocateRegister(Reg) &&
  "We have an unallocated variable which should have been handled");
   continue;
@@ -2512,7 +2514,6 @@ void RAGreedy::tryHintRecoloring(const LiveInterval 
&VirtReg) {
 // Get the live interval mapped with this virtual register to be able
 // to check for the interference with the new color.
 LiveInterval &LI = LIS->getInterval(Reg);
-MCRegister CurrPhys = VRM->getPhys(Reg);
 // Check that the new color matches the register class constraints and
 // that it is free for this live range.
 if (CurrPhys != PhysReg && (!MRI->getRegClass(Reg)->contains(PhysReg) ||

``




https://github.com/llvm/llvm-project/pull/160485
___
llvm-branch-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits


[llvm-branch-commits] [flang] [flang][OpenMP] Use OmpDirectiveSpecification in DECLARE_TARGET (PR #160573)

2025-09-24 Thread Krzysztof Parzyszek via llvm-branch-commits

https://github.com/kparzysz updated 
https://github.com/llvm/llvm-project/pull/160573

>From 525f12fa0da6c22dded6c19e2338b6bcc3c2da6f Mon Sep 17 00:00:00 2001
From: Krzysztof Parzyszek 
Date: Wed, 24 Sep 2025 07:59:16 -0500
Subject: [PATCH 1/3] [flang][OpenMP] Use OmpDirectiveSpecification in
 DECLARE_TARGET

---
 flang/include/flang/Parser/openmp-utils.h |   2 -
 flang/include/flang/Parser/parse-tree.h   |  10 +-
 flang/lib/Lower/OpenMP/OpenMP.cpp |  14 +-
 flang/lib/Parser/openmp-parsers.cpp   |  18 +-
 flang/lib/Parser/unparse.cpp  |   4 +-
 flang/lib/Semantics/check-omp-structure.cpp   | 245 +-
 flang/lib/Semantics/check-omp-structure.h |   3 -
 flang/lib/Semantics/resolve-directives.cpp|  27 +-
 flang/lib/Semantics/resolve-names.cpp |  77 +++---
 .../OpenMP/declare-target-indirect-tree.f90   |  28 +-
 .../OpenMP/declare-target-to-clause.f90   |  14 +-
 .../OpenMP/declare_target-device_type.f90 | 108 ++--
 .../Parser/OpenMP/enter-automap-modifier.f90  |  11 +-
 .../OpenMP/openmp6-directive-spellings.f90|   9 +-
 .../Semantics/OpenMP/blank-common-block.f90   |   1 +
 ...lare-target-function-name-with-symbols.f90 |   2 +-
 16 files changed, 319 insertions(+), 254 deletions(-)

diff --git a/flang/include/flang/Parser/openmp-utils.h 
b/flang/include/flang/Parser/openmp-utils.h
index 4b8fe6a5b49f0..bf54f970a7d3a 100644
--- a/flang/include/flang/Parser/openmp-utils.h
+++ b/flang/include/flang/Parser/openmp-utils.h
@@ -41,7 +41,6 @@ struct ConstructId {
 MAKE_CONSTR_ID(OpenMPDeclarativeAllocate, D::OMPD_allocate);
 MAKE_CONSTR_ID(OpenMPDeclarativeAssumes, D::OMPD_assumes);
 MAKE_CONSTR_ID(OpenMPDeclareReductionConstruct, D::OMPD_declare_reduction);
-MAKE_CONSTR_ID(OpenMPDeclareTargetConstruct, D::OMPD_declare_target);
 MAKE_CONSTR_ID(OpenMPExecutableAllocate, D::OMPD_allocate);
 MAKE_CONSTR_ID(OpenMPRequiresConstruct, D::OMPD_requires);
 
@@ -97,7 +96,6 @@ struct DirectiveNameScope {
   } else if constexpr (std::is_same_v ||
   std::is_same_v ||
   std::is_same_v ||
-  std::is_same_v ||
   std::is_same_v ||
   std::is_same_v) {
 return MakeName(std::get(x.t).source, ConstructId::id);
diff --git a/flang/include/flang/Parser/parse-tree.h 
b/flang/include/flang/Parser/parse-tree.h
index be30a95763208..e7593d9875097 100644
--- a/flang/include/flang/Parser/parse-tree.h
+++ b/flang/include/flang/Parser/parse-tree.h
@@ -4961,10 +4961,16 @@ struct OmpDeclareTargetSpecifier {
   std::variant u;
 };
 
+// Ref: [4.5:110-113], [5.0:180-185], [5.1:210-216], [5.2:206-207],
+//  [6.0:346-348]
+//
+// declare-target-directive ->  // since 4.5
+//DECLARE_TARGET[(extended-list)] |
+//DECLARE_TARGET clause-list
 struct OpenMPDeclareTargetConstruct {
-  TUPLE_CLASS_BOILERPLATE(OpenMPDeclareTargetConstruct);
+  WRAPPER_CLASS_BOILERPLATE(
+  OpenMPDeclareTargetConstruct, OmpDirectiveSpecification);
   CharBlock source;
-  std::tuple t;
 };
 
 // OMP v5.2: 5.8.8
diff --git a/flang/lib/Lower/OpenMP/OpenMP.cpp 
b/flang/lib/Lower/OpenMP/OpenMP.cpp
index d2e865b3e1d0c..1cb3335abbd06 100644
--- a/flang/lib/Lower/OpenMP/OpenMP.cpp
+++ b/flang/lib/Lower/OpenMP/OpenMP.cpp
@@ -761,19 +761,17 @@ static void promoteNonCPtrUseDevicePtrArgsToUseDeviceAddr(
 static void getDeclareTargetInfo(
 lower::AbstractConverter &converter, semantics::SemanticsContext &semaCtx,
 lower::pft::Evaluation &eval,
-const parser::OpenMPDeclareTargetConstruct &declareTargetConstruct,
+const parser::OpenMPDeclareTargetConstruct &construct,
 mlir::omp::DeclareTargetOperands &clauseOps,
 llvm::SmallVectorImpl &symbolAndClause) {
-  const auto &spec =
-  std::get(declareTargetConstruct.t);
-  if (const auto *objectList{parser::Unwrap(spec.u)}) {
-ObjectList objects{makeObjects(*objectList, semaCtx)};
+
+  if (!construct.v.Arguments().v.empty()) {
+ObjectList objects{makeObjects(construct.v.Arguments(), semaCtx)};
 // Case: declare target(func, var1, var2)
 gatherFuncAndVarSyms(objects, mlir::omp::DeclareTargetCaptureClause::to,
  symbolAndClause, /*automap=*/false);
-  } else if (const auto *clauseList{
- parser::Unwrap(spec.u)}) {
-List clauses = makeClauses(*clauseList, semaCtx);
+  } else {
+List clauses = makeClauses(construct.v.Clauses(), semaCtx);
 if (clauses.empty()) {
   Fortran::lower::pft::FunctionLikeUnit *owningProc =
   eval.getOwningProcedure();
diff --git a/flang/lib/Parser/openmp-parsers.cpp 
b/flang/lib/Parser/openmp-parsers.cpp
index 0085576292ff5..bd080386c0aea 100644
--- a/flang/lib/Parser/openmp-parsers.cpp
+++ b/flang/lib/Parser/openmp-parsers.cpp
@@ -1773,23 +1773,11 @@ 
TYPE_PARSER(sourced(construct(
 IsDirective(llvm::omp::Directive::OMPD_declare_reduction)) >=
 Parser{})))
 
-// declare-target with list
-TYPE_PARSER(sourced(construct(
-parenth