[clang] [Clang][Sema] Fix exception specification comparison for functions with different template depths (PR #111561)

2024-10-08 Thread Krystian Stasiowski via cfe-commits

https://github.com/sdkrystian created 
https://github.com/llvm/llvm-project/pull/111561

Currently, we do not account for differences in template depth when comparing 
exception specifications for equivalence. This results in explicit 
specializations of member function templates specialized for an implicitly 
instantiated specialization of their enclosing class template & friend 
declarations being rejected when their exception specifications involve a 
template parameter, e.g.
```cpp
template
struct A {
  template
  void f() noexcept(B);
};

template<>
template
void A::f() noexcept(B); // error: exception specification in declaration 
does not match previous declaration
```

In order to compare the _noexcept-specifiers_ correctly, we need to normalize 
both expressions prior to comparing them (just like we do when comparing 
_constraint-expressions_). This patch implements this normalization. 

Note: In its current state, this patch just copies the code from 
`AreConstraintExpressionsEqual` to implement expression normalization for 
_noexcept-specifiers_. I plan to factor out the common code from 
`AreConstraintExpressionsEqual` and `AreExceptionSpecsEqual` prior to merging 
this patch.

Fixes #101330, closes #102267

>From da01bdac8a99a127a74073df4a505bdc936291e2 Mon Sep 17 00:00:00 2001
From: Krystian Stasiowski 
Date: Tue, 8 Oct 2024 12:54:26 -0400
Subject: [PATCH] [Clang][Sema] Fix exception specification comparison for
 functions with different template depths

---
 clang/include/clang/Sema/Sema.h |   5 ++
 clang/lib/Sema/SemaExceptionSpec.cpp| 105 +++-
 clang/test/CXX/basic/basic.link/p11.cpp |  37 +
 3 files changed, 146 insertions(+), 1 deletion(-)
 create mode 100644 clang/test/CXX/basic/basic.link/p11.cpp

diff --git a/clang/include/clang/Sema/Sema.h b/clang/include/clang/Sema/Sema.h
index 7ff9c2754a6fe0..eea950582929d9 100644
--- a/clang/include/clang/Sema/Sema.h
+++ b/clang/include/clang/Sema/Sema.h
@@ -5026,6 +5026,11 @@ class Sema final : public SemaBase {
   /// special member function.
   void EvaluateImplicitExceptionSpec(SourceLocation Loc, FunctionDecl *FD);
 
+  bool AreExceptionSpecsEqual(const NamedDecl *Old,
+  const Expr *OldExceptionSpec,
+  const NamedDecl *New,
+  const Expr *NewExceptionSpec);
+
   /// Check the given exception-specification and update the
   /// exception specification information with the results.
   void checkExceptionSpecification(bool IsTopLevel,
diff --git a/clang/lib/Sema/SemaExceptionSpec.cpp 
b/clang/lib/Sema/SemaExceptionSpec.cpp
index dbddd6c370aa07..c74686073df228 100644
--- a/clang/lib/Sema/SemaExceptionSpec.cpp
+++ b/clang/lib/Sema/SemaExceptionSpec.cpp
@@ -10,7 +10,6 @@
 //
 
//===--===//
 
-#include "clang/Sema/SemaInternal.h"
 #include "clang/AST/ASTMutationListener.h"
 #include "clang/AST/CXXInheritance.h"
 #include "clang/AST/Expr.h"
@@ -19,6 +18,9 @@
 #include "clang/AST/TypeLoc.h"
 #include "clang/Basic/Diagnostic.h"
 #include "clang/Basic/SourceManager.h"
+#include "clang/Sema/EnterExpressionEvaluationContext.h"
+#include "clang/Sema/SemaInternal.h"
+#include "clang/Sema/Template.h"
 #include "llvm/ADT/SmallPtrSet.h"
 #include "llvm/ADT/SmallString.h"
 #include 
@@ -314,6 +316,22 @@ bool Sema::CheckEquivalentExceptionSpec(FunctionDecl *Old, 
FunctionDecl *New) {
 return false;
   }
 
+  if (Old->getExceptionSpecType() == EST_DependentNoexcept &&
+  New->getExceptionSpecType() == EST_DependentNoexcept) {
+const auto *OldType = Old->getType()->getAs();
+const auto *NewType = New->getType()->getAs();
+OldType = ResolveExceptionSpec(New->getLocation(), OldType);
+if (!OldType)
+  return false;
+NewType = ResolveExceptionSpec(New->getLocation(), NewType);
+if (!NewType)
+  return false;
+
+if (AreExceptionSpecsEqual(Old, OldType->getNoexceptExpr(), New,
+   NewType->getNoexceptExpr()))
+  return false;
+  }
+
   // Check the types as written: they must match before any exception
   // specification adjustment is applied.
   if (!CheckEquivalentExceptionSpecImpl(
@@ -501,6 +519,89 @@ bool Sema::CheckEquivalentExceptionSpec(
   return Result;
 }
 
+static const Expr *SubstituteExceptionSpecWithoutEvaluation(
+Sema &S, const Sema::TemplateCompareNewDeclInfo &DeclInfo,
+const Expr *ExceptionSpec) {
+  MultiLevelTemplateArgumentList MLTAL = S.getTemplateInstantiationArgs(
+  DeclInfo.getDecl(), DeclInfo.getLexicalDeclContext(),
+  /*Final=*/false, /*Innermost=*/std::nullopt,
+  /*RelativeToPrimary=*/true, /*ForConstraintInstantiation=*/true);
+
+  if (!MLTAL.getNumSubstitutedLevels())
+return ExceptionSpec;
+
+  Sema::SFINAETrap SFINAE(S, /*AccessCheckingSFINAE=*/false);
+
+  Sema::InstantiatingTemplate Inst(
+  S, DeclInfo.getLocation(),
+  const_cast(

[clang] Reapply "[Clang][Sema] Refactor collection of multi-level template argument lists (#106585)" (PR #111173)

2024-10-08 Thread Matheus Izvekov via cfe-commits

mizvekov wrote:

Yeah, I think its only user was reverted a while ago, but should be merged back 
eventually.

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


[clang] [clang] Add test for CWG110 "Can template functions and classes be declared in the same scope?" (PR #111446)

2024-10-08 Thread Vlad Serebrennikov via cfe-commits

https://github.com/Endilll edited 
https://github.com/llvm/llvm-project/pull/111446
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] assume_aligned incorrectly diagnoses a dependent return type (PR #111573)

2024-10-08 Thread Erich Keane via cfe-commits


@@ -1216,6 +1216,8 @@ static void handlePreferredName(Sema &S, Decl *D, const 
ParsedAttr &AL) {
 }
 
 bool Sema::isValidPointerAttrType(QualType T, bool RefOkay) {
+  if (T->isDependentType())

erichkeane wrote:

Probably valuable to audit the other uses of this function well, and remove 
checks for dependence there as redundant.  And probably ensure the 
documentation of this function mentions that it skips on dependence.

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


[clang] [clang] Add test for CWG110 "Can template functions and classes be declared in the same scope?" (PR #111446)

2024-10-08 Thread Vlad Serebrennikov via cfe-commits

https://github.com/Endilll edited 
https://github.com/llvm/llvm-project/pull/111446
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Add test for CWG110 "Can template functions and classes be declared in the same scope?" (PR #111446)

2024-10-08 Thread Vlad Serebrennikov via cfe-commits

https://github.com/Endilll closed 
https://github.com/llvm/llvm-project/pull/111446
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] eaea5f6 - [clang] Add test for CWG110 "Can template functions and classes be declared in the same scope?" (#111446)

2024-10-08 Thread via cfe-commits

Author: Vlad Serebrennikov
Date: 2024-10-08T22:41:33+04:00
New Revision: eaea5f6f952b6059cebfe87ea9800a3a6516f9ed

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

LOG: [clang] Add test for CWG110 "Can template functions and classes be 
declared in the same scope?" (#111446)

[P1787R6](https://wg21.link/p1787r6):
> [CWG110](https://cplusplus.github.io/CWG/issues/110.html) is resolved
by reducing the restriction in [temp.pre] to a note (matching the
behavior of GCC, Clang, and ICC).

Wording: see changes to [temp.pre]/7

I believe the wording for the questions raised in the issue is now the
definition of corresponding declarations that is given in
[[basic.scope.scope]/4](https://eel.is/c++draft/basic.scope#scope-4):
> Two declarations correspond if they (re)introduce the same name, both
declare constructors, or both declare destructors, unless
> — either is a using-declarator, or
> — one declares a type (not a typedef-name) and the other declares a
variable, non-static data member other than of an anonymous union
([class.union.anon]), enumerator, function, or function template, or
> — each declares a function or function template and they do not
declare corresponding overloads.

Then it's used as an input for the definition of potentially conflicting
declarations given in
[[basic.scope.scope]/6](https://eel.is/c++draft/basic.scope#scope-6).

Answering the question in the title: yes, having a function template and
a type with the same name that has the same target scope is well-formed.

A keen eye might spot that the current
[[temp.pre]/7](https://eel.is/c++draft/temp.pre#7) note doesn't reflect
all of the exceptions from the definition of corresponding declarations
in [basic.scope.scope]/4, namely 4.1 and 4.2. I believe the note is
defective, and I opened an editorial PR against the draft to fix that:
https://github.com/cplusplus/draft/pull/7284.

Added: 


Modified: 
clang/test/CXX/drs/cwg1xx.cpp
clang/www/cxx_dr_status.html

Removed: 




diff  --git a/clang/test/CXX/drs/cwg1xx.cpp b/clang/test/CXX/drs/cwg1xx.cpp
index d6ee0844458b1d..6aec8b65c91f12 100644
--- a/clang/test/CXX/drs/cwg1xx.cpp
+++ b/clang/test/CXX/drs/cwg1xx.cpp
@@ -119,6 +119,20 @@ namespace cwg109 { // cwg109: yes
   };
 }
 
+namespace cwg110 { // cwg110: 2.8
+template 
+void f(T);
+
+class f {};
+
+template 
+void f(T, T);
+
+class f g;
+void (*h)(int) = static_cast(f);
+void (*i)(int, int) = static_cast(f);
+} // namespace cwg110
+
 namespace cwg111 { // cwg111: dup 535
   struct A { A(); A(volatile A&, int = 0); A(A&, const char * = "foo"); };
   struct B : A { B(); }; // #cwg111-B

diff  --git a/clang/www/cxx_dr_status.html b/clang/www/cxx_dr_status.html
index ba63106ccc3875..1a67b6103cf43e 100755
--- a/clang/www/cxx_dr_status.html
+++ b/clang/www/cxx_dr_status.html
@@ -705,7 +705,7 @@ C++ defect report implementation status
 https://cplusplus.github.io/CWG/issues/110.html";>110
 CD6
 Can template functions and classes be declared in the same scope?
-Unknown
+Clang 2.8
   
   
 https://cplusplus.github.io/CWG/issues/111.html";>111



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [HLSL] Make HLSLAttributedResourceType canonical and add code paths to convert HLSL types to DirectX target types (PR #110327)

2024-10-08 Thread Chris B via cfe-commits

https://github.com/llvm-beanz edited 
https://github.com/llvm/llvm-project/pull/110327
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [HLSL] Make HLSLAttributedResourceType canonical and add code paths to convert HLSL types to DirectX target types (PR #110327)

2024-10-08 Thread Chris B via cfe-commits


@@ -32,6 +32,7 @@
 #include "llvm/ADT/SmallVector.h"
 #include "llvm/ADT/StringExtras.h"
 #include "llvm/Support/CRC.h"
+#include "llvm/Support/DXILABI.h"

llvm-beanz wrote:

Do we need this include?

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


[clang-tools-extra] [clang-tidy][performance-move-const-arg] Fix crash when argument type has no definition (PR #111472)

2024-10-08 Thread Julian Schmidt via cfe-commits

https://github.com/5chmidti approved this pull request.

Please add a release note, otherwise LGTM

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


[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)

2024-10-08 Thread Finn Plummer via cfe-commits


@@ -428,6 +431,7 @@ bool SPIRVInstructionSelector::spvSelect(Register ResVReg,
 
   case TargetOpcode::G_INTRINSIC:
   case TargetOpcode::G_INTRINSIC_W_SIDE_EFFECTS:
+  case TargetOpcode::G_INTRINSIC_CONVERGENT:

inbelic wrote:

Afaict, not within this section of the codebase, it is used elsewhere though eg 
`GlobalISel`. But I think @Keenuts would be able to better elaborate.

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


[clang] Support BasedOnStyle referencing an arbitrary file (PR #110634)

2024-10-08 Thread Ryan Saunders via cfe-commits

https://github.com/jediry updated 
https://github.com/llvm/llvm-project/pull/110634

>From 82160d1e6de3f197c847bf8ed21ea1fc314b3cf4 Mon Sep 17 00:00:00 2001
From: Ryan Saunders 
Date: Tue, 1 Oct 2024 00:03:50 -0700
Subject: [PATCH 1/2] Support BasedOnStyle: file:blah.clang-format

---
 clang/include/clang/Format/Format.h |  22 ++-
 clang/lib/Format/Format.cpp | 207 +---
 2 files changed, 174 insertions(+), 55 deletions(-)

diff --git a/clang/include/clang/Format/Format.h 
b/clang/include/clang/Format/Format.h
index d8b62c7652a0f6..1b833256500431 100644
--- a/clang/include/clang/Format/Format.h
+++ b/clang/include/clang/Format/Format.h
@@ -53,10 +53,24 @@ std::error_code make_error_code(ParseError e);
 /// The ``FormatStyle`` is used to configure the formatting to follow
 /// specific guidelines.
 struct FormatStyle {
-  // If the BasedOn: was InheritParentConfig and this style needs the file from
-  // the parent directories. It is not part of the actual style for formatting.
-  // Thus the // instead of ///.
-  bool InheritsParentConfig;
+  // If the BasedOnStyle: was InheritParentConfig, this is the string
+  // "", indicating to search upwards until a _clang-format or
+  // .clang-format file is found.
+  //
+  // Else, if the BasedOnStyle: was an explicit "file:" reference, this is
+  // that reference, verbatim, including the "file:" prefix. The string
+  // after "file:" may start with $(CLANG_FORMAT_DIR), in which case the value
+  // of the CLANG_FORMAT_DIR environment variable (which must be defined) is
+  // substituted; otherwise, the string after "file:" is interpreted as a
+  // path relative to the current config file. (Absolute paths are not
+  // permitted, for security reasons.)
+  //
+  // Else (i.e., if the BasedOnStyle is omitted or a predefined style), this is
+  // the empty string.
+  //
+  // This field is not part of the actual style for formatting, thus the //
+  // instead of ///.
+  std::string InheritsConfig;
 
   /// The extra indent or outdent of access modifiers, e.g. ``public:``.
   /// \version 3.3
diff --git a/clang/lib/Format/Format.cpp b/clang/lib/Format/Format.cpp
index d2463b892fbb96..bfca01d1a67230 100644
--- a/clang/lib/Format/Format.cpp
+++ b/clang/lib/Format/Format.cpp
@@ -1543,7 +1543,7 @@ FormatStyle getLLVMStyle(FormatStyle::LanguageKind 
Language) {
   LLVMStyle.IndentRequiresClause = true;
   LLVMStyle.IndentWidth = 2;
   LLVMStyle.IndentWrappedFunctionNames = false;
-  LLVMStyle.InheritsParentConfig = false;
+  LLVMStyle.InheritsConfig.clear();
   LLVMStyle.InsertBraces = false;
   LLVMStyle.InsertNewlineAtEOF = false;
   LLVMStyle.InsertTrailingCommas = FormatStyle::TCS_None;
@@ -1992,7 +1992,9 @@ bool getPredefinedStyle(StringRef Name, 
FormatStyle::LanguageKind Language,
   else if (Name.equals_insensitive("none"))
 *Style = getNoStyle();
   else if (Name.equals_insensitive("inheritparentconfig"))
-Style->InheritsParentConfig = true;
+Style->InheritsConfig = "";
+  else if (Name.starts_with_insensitive("file:"))
+Style->InheritsConfig = Name;
   else
 return false;
 
@@ -4004,6 +4006,45 @@ loadAndParseConfigFile(StringRef ConfigFile, 
llvm::vfs::FileSystem *FS,
   return Text;
 }
 
+// Resolves an explicit file: reference in a BasedOnStyle directive to a
+// canonical, absolute path, substituting the value of the CLANG_FORMAT_DIR
+// environment variable if the path starts with $(CLANG_FORMAT_DIR), or 
treating
+// BasedOnFile as relative to the current ConfigFile otherwise.
+static Expected>
+resolveExplicitParentConfigFile(StringRef ConfigFile, StringRef BasedOnFile,
+llvm::vfs::FileSystem *FS) {
+  constexpr const char *EnvVar = "CLANG_FORMAT_DIR";
+  constexpr const char *EnvVarExpansion = "$(CLANG_FORMAT_DIR)";
+  if (BasedOnFile.starts_with(EnvVarExpansion)) {
+const char *ClangFormatDir = getenv(EnvVar);
+if (ClangFormatDir == nullptr) {
+  return make_string_error(ConfigFile + ": 'BasedOnStyle: " + BasedOnFile +
+   "' uses " + EnvVarExpansion + ", but the " +
+   EnvVar + " environment variable is not 
defined");
+} else {
+  auto Status = FS->status(ClangFormatDir);
+  if (!Status ||
+  Status->getType() != llvm::sys::fs::file_type::directory_file) {
+return make_string_error(
+StringRef("Environment variable ") + EnvVar + " = " +
+ClangFormatDir + "does not refer to a valid, readable directory");
+  }
+
+  SmallString<128> FileName{ClangFormatDir};
+  llvm::sys::path::append(FileName,
+  BasedOnFile.substr(strlen(EnvVarExpansion)));
+  ;
+  llvm::sys::path::remove_dots(FileName, true /*remove_dot_dot*/);
+  return FileName;
+}
+  } else {
+SmallString<128> FileName = llvm::sys::path::parent_path(ConfigFile);
+llvm::sys::path::append(FileName, BasedOnFile);
+llvm::sys::path::re

[clang] [llvm] [clang][llvm][SPIR-V] Explicitly encode native integer widths for SPIR-V (PR #110695)

2024-10-08 Thread Vyacheslav Levytskyy via cfe-commits


@@ -1,12 +1,14 @@
 ; This test aims to check ability to support "Arithmetic with Overflow" 
intrinsics
 ; in the special case when those intrinsics are being generated by the 
CodeGenPrepare;
-; pass during translations with optimization (note -O3 in llc arguments).
+; pass during translations with optimization (note -disable-lsr, to inhibit
+; strength reduction pre-empting with a more preferable match for this pattern
+; in llc arguments).
 
-; RUN: llc -O3 -mtriple=spirv32-unknown-unknown %s -o - | FileCheck %s
-; RUN: %if spirv-tools %{ llc -O3 -mtriple=spirv32-unknown-unknown %s -o - 
-filetype=obj | spirv-val %}
+; RUN: llc -O3 -disable-lsr -mtriple=spirv32-unknown-unknown %s -o - | 
FileCheck %s

VyacheslavLevytskyy wrote:

Happy to help with motivation. The original intent is to have a minimized 
reproducer of an issue as a part of the test suite. The point of the test case 
is to feed SPIR-V Backend with LLVM IR without saturation arithmetic intrinsics 
and ensure that SPIR-V Backend is able to deal with those intrinsics appearing 
along the way in translation. There is a separate test case in the test suite 
for the same intrinsics explicitly represented in the input LLVM IR, and it's 
another case, different from this one.

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


[clang] [llvm] [CGData][ThinLTO] Global Outlining with Two-CodeGen Rounds (PR #90933)

2024-10-08 Thread Kyungwoo Lee via cfe-commits

https://github.com/kyulee-com updated 
https://github.com/llvm/llvm-project/pull/90933

>From 411fc459e58a65d9599c917f220ba68bb799baac Mon Sep 17 00:00:00 2001
From: Kyungwoo Lee 
Date: Fri, 13 Sep 2024 08:51:00 -0700
Subject: [PATCH 1/4] [CGData][ThinLTO] Global Outlining with Two-CodeGen
 Rounds

---
 llvm/include/llvm/CGData/CodeGenData.h|  16 +++
 llvm/lib/CGData/CodeGenData.cpp   |  81 +-
 llvm/lib/LTO/CMakeLists.txt   |   1 +
 llvm/lib/LTO/LTO.cpp  | 103 +-
 llvm/lib/LTO/LTOBackend.cpp   |  11 ++
 .../test/ThinLTO/AArch64/cgdata-two-rounds.ll |  94 
 llvm/test/ThinLTO/AArch64/lit.local.cfg   |   2 +
 7 files changed, 302 insertions(+), 6 deletions(-)
 create mode 100644 llvm/test/ThinLTO/AArch64/cgdata-two-rounds.ll
 create mode 100644 llvm/test/ThinLTO/AArch64/lit.local.cfg

diff --git a/llvm/include/llvm/CGData/CodeGenData.h 
b/llvm/include/llvm/CGData/CodeGenData.h
index 84133a433170fe..1e1afe99327650 100644
--- a/llvm/include/llvm/CGData/CodeGenData.h
+++ b/llvm/include/llvm/CGData/CodeGenData.h
@@ -164,6 +164,22 @@ publishOutlinedHashTree(std::unique_ptr 
HashTree) {
   CodeGenData::getInstance().publishOutlinedHashTree(std::move(HashTree));
 }
 
+/// Initialize the two-codegen rounds.
+void initializeTwoCodegenRounds();
+
+/// Save the current module before the first codegen round.
+void saveModuleForTwoRounds(const Module &TheModule, unsigned Task);
+
+/// Load the current module before the second codegen round.
+std::unique_ptr loadModuleForTwoRounds(BitcodeModule &OrigModule,
+   unsigned Task,
+   LLVMContext &Context);
+
+/// Merge the codegen data from the input files in scratch vector in ThinLTO
+/// two-codegen rounds.
+Error mergeCodeGenData(
+const std::unique_ptr>> InputFiles);
+
 void warn(Error E, StringRef Whence = "");
 void warn(Twine Message, std::string Whence = "", std::string Hint = "");
 
diff --git a/llvm/lib/CGData/CodeGenData.cpp b/llvm/lib/CGData/CodeGenData.cpp
index 55d2504231c744..ff8e5dd7c75790 100644
--- a/llvm/lib/CGData/CodeGenData.cpp
+++ b/llvm/lib/CGData/CodeGenData.cpp
@@ -17,6 +17,7 @@
 #include "llvm/Object/ObjectFile.h"
 #include "llvm/Support/CommandLine.h"
 #include "llvm/Support/FileSystem.h"
+#include "llvm/Support/Path.h"
 #include "llvm/Support/WithColor.h"
 
 #define DEBUG_TYPE "cg-data"
@@ -30,6 +31,14 @@ cl::opt
 cl::opt
 CodeGenDataUsePath("codegen-data-use-path", cl::init(""), cl::Hidden,
cl::desc("File path to where .cgdata file is read"));
+cl::opt CodeGenDataThinLTOTwoRounds(
+"codegen-data-thinlto-two-rounds", cl::init(false), cl::Hidden,
+cl::desc("Enable two-round ThinLTO code generation. The first round "
+ "emits codegen data, while the second round uses the emitted "
+ "codegen data for further optimizations."));
+
+// Path to where the optimized bitcodes are saved and restored for ThinLTO.
+static SmallString<128> CodeGenDataThinLTOTwoRoundsPath;
 
 static std::string getCGDataErrString(cgdata_error Err,
   const std::string &ErrMsg = "") {
@@ -139,7 +148,7 @@ CodeGenData &CodeGenData::getInstance() {
   std::call_once(CodeGenData::OnceFlag, []() {
 Instance = std::unique_ptr(new CodeGenData());
 
-if (CodeGenDataGenerate)
+if (CodeGenDataGenerate || CodeGenDataThinLTOTwoRounds)
   Instance->EmitCGData = true;
 else if (!CodeGenDataUsePath.empty()) {
   // Initialize the global CGData if the input file name is given.
@@ -215,6 +224,76 @@ void warn(Error E, StringRef Whence) {
   }
 }
 
+static std::string getPath(StringRef Dir, unsigned Task) {
+  return (Dir + "/" + llvm::Twine(Task) + ".saved_copy.bc").str();
+}
+
+void initializeTwoCodegenRounds() {
+  assert(CodeGenDataThinLTOTwoRounds);
+  if (auto EC = llvm::sys::fs::createUniqueDirectory(
+  "cgdata", CodeGenDataThinLTOTwoRoundsPath))
+report_fatal_error(Twine("Failed to create directory: ") + EC.message());
+}
+
+void saveModuleForTwoRounds(const Module &TheModule, unsigned Task) {
+  assert(sys::fs::is_directory(CodeGenDataThinLTOTwoRoundsPath));
+  std::string Path = getPath(CodeGenDataThinLTOTwoRoundsPath, Task);
+  std::error_code EC;
+  raw_fd_ostream OS(Path, EC, sys::fs::OpenFlags::OF_None);
+  if (EC)
+report_fatal_error(Twine("Failed to open ") + Path +
+   " to save optimized bitcode: " + EC.message());
+  WriteBitcodeToFile(TheModule, OS, /* ShouldPreserveUseListOrder */ true);
+}
+
+std::unique_ptr loadModuleForTwoRounds(BitcodeModule &OrigModule,
+   unsigned Task,
+   LLVMContext &Context) {
+  assert(sys::fs::is_directory(CodeGenDataThinLTOTwoRoundsPath));
+  std::string Path = getPath(CodeGenDataThinLTOTwoRoun

[clang] Support BasedOnStyle referencing an arbitrary file (PR #110634)

2024-10-08 Thread Ryan Saunders via cfe-commits

https://github.com/jediry updated 
https://github.com/llvm/llvm-project/pull/110634

>From 82160d1e6de3f197c847bf8ed21ea1fc314b3cf4 Mon Sep 17 00:00:00 2001
From: Ryan Saunders 
Date: Tue, 1 Oct 2024 00:03:50 -0700
Subject: [PATCH 1/2] Support BasedOnStyle: file:blah.clang-format

---
 clang/include/clang/Format/Format.h |  22 ++-
 clang/lib/Format/Format.cpp | 207 +---
 2 files changed, 174 insertions(+), 55 deletions(-)

diff --git a/clang/include/clang/Format/Format.h 
b/clang/include/clang/Format/Format.h
index d8b62c7652a0f6..1b833256500431 100644
--- a/clang/include/clang/Format/Format.h
+++ b/clang/include/clang/Format/Format.h
@@ -53,10 +53,24 @@ std::error_code make_error_code(ParseError e);
 /// The ``FormatStyle`` is used to configure the formatting to follow
 /// specific guidelines.
 struct FormatStyle {
-  // If the BasedOn: was InheritParentConfig and this style needs the file from
-  // the parent directories. It is not part of the actual style for formatting.
-  // Thus the // instead of ///.
-  bool InheritsParentConfig;
+  // If the BasedOnStyle: was InheritParentConfig, this is the string
+  // "", indicating to search upwards until a _clang-format or
+  // .clang-format file is found.
+  //
+  // Else, if the BasedOnStyle: was an explicit "file:" reference, this is
+  // that reference, verbatim, including the "file:" prefix. The string
+  // after "file:" may start with $(CLANG_FORMAT_DIR), in which case the value
+  // of the CLANG_FORMAT_DIR environment variable (which must be defined) is
+  // substituted; otherwise, the string after "file:" is interpreted as a
+  // path relative to the current config file. (Absolute paths are not
+  // permitted, for security reasons.)
+  //
+  // Else (i.e., if the BasedOnStyle is omitted or a predefined style), this is
+  // the empty string.
+  //
+  // This field is not part of the actual style for formatting, thus the //
+  // instead of ///.
+  std::string InheritsConfig;
 
   /// The extra indent or outdent of access modifiers, e.g. ``public:``.
   /// \version 3.3
diff --git a/clang/lib/Format/Format.cpp b/clang/lib/Format/Format.cpp
index d2463b892fbb96..bfca01d1a67230 100644
--- a/clang/lib/Format/Format.cpp
+++ b/clang/lib/Format/Format.cpp
@@ -1543,7 +1543,7 @@ FormatStyle getLLVMStyle(FormatStyle::LanguageKind 
Language) {
   LLVMStyle.IndentRequiresClause = true;
   LLVMStyle.IndentWidth = 2;
   LLVMStyle.IndentWrappedFunctionNames = false;
-  LLVMStyle.InheritsParentConfig = false;
+  LLVMStyle.InheritsConfig.clear();
   LLVMStyle.InsertBraces = false;
   LLVMStyle.InsertNewlineAtEOF = false;
   LLVMStyle.InsertTrailingCommas = FormatStyle::TCS_None;
@@ -1992,7 +1992,9 @@ bool getPredefinedStyle(StringRef Name, 
FormatStyle::LanguageKind Language,
   else if (Name.equals_insensitive("none"))
 *Style = getNoStyle();
   else if (Name.equals_insensitive("inheritparentconfig"))
-Style->InheritsParentConfig = true;
+Style->InheritsConfig = "";
+  else if (Name.starts_with_insensitive("file:"))
+Style->InheritsConfig = Name;
   else
 return false;
 
@@ -4004,6 +4006,45 @@ loadAndParseConfigFile(StringRef ConfigFile, 
llvm::vfs::FileSystem *FS,
   return Text;
 }
 
+// Resolves an explicit file: reference in a BasedOnStyle directive to a
+// canonical, absolute path, substituting the value of the CLANG_FORMAT_DIR
+// environment variable if the path starts with $(CLANG_FORMAT_DIR), or 
treating
+// BasedOnFile as relative to the current ConfigFile otherwise.
+static Expected>
+resolveExplicitParentConfigFile(StringRef ConfigFile, StringRef BasedOnFile,
+llvm::vfs::FileSystem *FS) {
+  constexpr const char *EnvVar = "CLANG_FORMAT_DIR";
+  constexpr const char *EnvVarExpansion = "$(CLANG_FORMAT_DIR)";
+  if (BasedOnFile.starts_with(EnvVarExpansion)) {
+const char *ClangFormatDir = getenv(EnvVar);
+if (ClangFormatDir == nullptr) {
+  return make_string_error(ConfigFile + ": 'BasedOnStyle: " + BasedOnFile +
+   "' uses " + EnvVarExpansion + ", but the " +
+   EnvVar + " environment variable is not 
defined");
+} else {
+  auto Status = FS->status(ClangFormatDir);
+  if (!Status ||
+  Status->getType() != llvm::sys::fs::file_type::directory_file) {
+return make_string_error(
+StringRef("Environment variable ") + EnvVar + " = " +
+ClangFormatDir + "does not refer to a valid, readable directory");
+  }
+
+  SmallString<128> FileName{ClangFormatDir};
+  llvm::sys::path::append(FileName,
+  BasedOnFile.substr(strlen(EnvVarExpansion)));
+  ;
+  llvm::sys::path::remove_dots(FileName, true /*remove_dot_dot*/);
+  return FileName;
+}
+  } else {
+SmallString<128> FileName = llvm::sys::path::parent_path(ConfigFile);
+llvm::sys::path::append(FileName, BasedOnFile);
+llvm::sys::path::re

[clang] [llvm] [BPF] Add load-acquire and store-release instructions under -mcpu=v4 (PR #108636)

2024-10-08 Thread via cfe-commits

yonghong-song wrote:

For

About whether we should sign-extend for 8- and 16-bit load-acquires (brought up 
by Yonghong):

All ARM64 insns that match acquiring_load seem to 
zero-extend the value before writing it to register, like, LDAPRH:

Load-Acquire RCpc Register Halfword derives an address from a base register 
value, loads a halfword from the derived address in memory, zero-extends it and 
writes it to a register.

So right now I'm keeping our LDBACQ32 and LDHACQ32 to zero-extend. I'll take a 
look at other archs later.


I think you need to implement kernel part to utilize the newly-introduced bpf 
insns. Then we can see whether jit'ed code works as expected or not.

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


[clang] Support BasedOnStyle referencing an arbitrary file (PR #110634)

2024-10-08 Thread Ryan Saunders via cfe-commits

jediry wrote:

> Can this have some unit test?

Done. Added docs as well.

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


[clang] Format clang/lib/Sema/Sema.cpp (PR #111518)

2024-10-08 Thread Aaron Ballman via cfe-commits

AaronBallman wrote:

Is there a need for the changes? (Are you making a significant number of 
changes in the file, or is this just a drive-by cleanup?) Generally, we don't 
do sweeping formatting changes:

> Avoid committing formatting- or whitespace-only changes outside of code you 
> plan to make subsequent changes to. Also, try to separate formatting or 
> whitespace changes from functional changes, either by correcting the format 
> first (ideally) or afterward. Such changes should be highly localized and the 
> commit message should clearly state that the commit is not intended to change 
> functionality, usually by stating it is NFC. (From 
> https://llvm.org/docs/DeveloperPolicy.html#obtaining-commit-access)

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


[clang] 7e31eaa - [libc++] Remove unused HAVE_LIBCXXABI variable from Android cache (#111007)

2024-10-08 Thread via cfe-commits

Author: Louis Dionne
Date: 2024-10-08T13:16:47-04:00
New Revision: 7e31eaab575d15384654ed989717e5579e963e72

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

LOG: [libc++] Remove unused HAVE_LIBCXXABI variable from Android cache (#111007)

This variable isn't used anymore in libc++'s build and hasn't been for a
few years, so this is likely a remnant of the past.

Added: 


Modified: 
clang/cmake/caches/Android.cmake

Removed: 




diff  --git a/clang/cmake/caches/Android.cmake 
b/clang/cmake/caches/Android.cmake
index 9e15fff0337612..d5ca6b50d4ada7 100644
--- a/clang/cmake/caches/Android.cmake
+++ b/clang/cmake/caches/Android.cmake
@@ -9,7 +9,6 @@ set(CLANG_VENDOR Android CACHE STRING "")
 
 set(CMAKE_BUILD_TYPE RELEASE CACHE STRING "")
 
-set(HAVE_LIBCXXABI ON CACHE BOOL "")
 set(LLVM_BUILD_TOOLS OFF CACHE BOOL "")
 set(LLVM_ENABLE_ASSERTIONS ON CACHE BOOL "")
 set(LLVM_ENABLE_THREADS OFF CACHE BOOL "")



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [libc++] Remove unused HAVE_LIBCXXABI variable from Android cache (PR #111007)

2024-10-08 Thread Louis Dionne via cfe-commits

https://github.com/ldionne closed 
https://github.com/llvm/llvm-project/pull/111007
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [Clang] Improve type traits recognition in `__has_builtin` (PR #111516)

2024-10-08 Thread via cfe-commits

https://github.com/cor3ntin updated 
https://github.com/llvm/llvm-project/pull/111516

>From 94874b7acb9ce763f502b74bc50d983ee3012d53 Mon Sep 17 00:00:00 2001
From: Corentin Jabot 
Date: Tue, 8 Oct 2024 12:28:24 +0200
Subject: [PATCH 1/2] [Clang] Improve type traits recognition in
 `__has_builtin`

`__has_builtin` was relying on reversible identifiers and
string matching to recognize builtin-type traits, leading
to some newer type traits not being recognized.

Fixes #111477
---
 clang/docs/ReleaseNotes.rst   |  2 +
 clang/include/clang/Basic/TokenKinds.def  |  5 ++-
 clang/lib/Lex/PPMacroExpansion.cpp| 52 ++-
 clang/test/Preprocessor/feature_tests.cpp |  5 ++-
 4 files changed, 43 insertions(+), 21 deletions(-)

diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index bd86fff6dd03fa..c1122e1180ab91 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -408,6 +408,8 @@ Bug Fixes to Compiler Builtins
 
 - ``__noop`` can now be used in a constant expression. (#GH102064)
 
+- Fix ``__has_builtin`` incorrectly returning ``false`` for some C++ type 
traits. (#GH111477)
+
 Bug Fixes to Attribute Support
 ^^
 
diff --git a/clang/include/clang/Basic/TokenKinds.def 
b/clang/include/clang/Basic/TokenKinds.def
index c5c3838407cf48..fdfb35de9cf287 100644
--- a/clang/include/clang/Basic/TokenKinds.def
+++ b/clang/include/clang/Basic/TokenKinds.def
@@ -64,6 +64,10 @@
 #ifndef EXPRESSION_TRAIT
 #define EXPRESSION_TRAIT(I,E,K) KEYWORD(I,K)
 #endif
+#ifndef TRANSFORM_TYPE_TRAIT_DEF
+#define TRANSFORM_TYPE_TRAIT_DEF(K, Trait) KEYWORD(__##Trait, KEYCXX)
+#endif
+
 #ifndef ALIAS
 #define ALIAS(X,Y,Z)
 #endif
@@ -534,7 +538,6 @@ TYPE_TRAIT_1(__has_unique_object_representations,
 TYPE_TRAIT_2(__is_layout_compatible, IsLayoutCompatible, KEYCXX)
 TYPE_TRAIT_2(__is_pointer_interconvertible_base_of, 
IsPointerInterconvertibleBaseOf, KEYCXX)
 
-#define TRANSFORM_TYPE_TRAIT_DEF(_, Trait) KEYWORD(__##Trait, KEYCXX)
 #include "clang/Basic/TransformTypeTraits.def"
 
 // Clang-only C++ Type Traits
diff --git a/clang/lib/Lex/PPMacroExpansion.cpp 
b/clang/lib/Lex/PPMacroExpansion.cpp
index 27d09b4c8ee744..d48bb8a9a9cded 100644
--- a/clang/lib/Lex/PPMacroExpansion.cpp
+++ b/clang/lib/Lex/PPMacroExpansion.cpp
@@ -1616,6 +1616,34 @@ 
asm("_ZNKSt8time_putIcSt19ostreambuf_iteratorIcSt11char_traitsIcEEE3putES3_"
 "RSt8ios_basecPK2tmPKcSB_");
 #endif
 
+static bool IsBuiltinTrait(Token &Tok) {
+
+#define TYPE_TRAIT_1(Spelling, Name, Key)  
\
+  case tok::kw_##Spelling: 
\
+return true;
+#define TYPE_TRAIT_2(Spelling, Name, Key)  
\
+  case tok::kw_##Spelling: 
\
+return true;
+#define TYPE_TRAIT_N(Spelling, Name, Key)  
\
+  case tok::kw_##Spelling: 
\
+return true;
+#define ARRAY_TYPE_TRAIT(Spelling, Name, Key)  
\
+  case tok::kw_##Spelling: 
\
+return true;
+#define EXPRESSION_TRAIT(Spelling, Name, Key)  
\
+  case tok::kw_##Spelling: 
\
+return true;
+#define TRANSFORM_TYPE_TRAIT_DEF(K, Spelling)  
\
+  case tok::kw___##Spelling:   
\
+return true;
+
+  switch (Tok.getKind()) {
+  default:
+return false;
+#include "clang/Basic/TokenKinds.def"
+  }
+}
+
 /// ExpandBuiltinMacro - If an identifier token is read that is to be expanded
 /// as a builtin macro, handle it and return the next token as 'Tok'.
 void Preprocessor::ExpandBuiltinMacro(Token &Tok) {
@@ -1814,25 +1842,11 @@ void Preprocessor::ExpandBuiltinMacro(Token &Tok) {
 getTargetInfo().getTargetOpts().FeatureMap);
   }
   return true;
-} else if (II->getTokenID() != tok::identifier ||
-   II->hasRevertedTokenIDToIdentifier()) {
-  // Treat all keywords that introduce a custom syntax of the form
-  //
-  //   '__some_keyword' '(' [...] ')'
-  //
-  // as being "builtin functions", even if the syntax isn't a valid
-  // function call (for example, because the builtin takes a type
-  // argument).
-  if (II->getName().starts_with("__builtin_") ||
-  II->getName().starts_with("__is_") ||
-  II->getName().starts_with("__has_"))
-return true;
-  return llvm::StringSwitch(II->getName())
-  .Case("__array_rank", true)
-  .Case("__array_extent", true)
-#define TRANSFORM_TYPE_TRAIT_DEF(_, Trait) .Case("__" #Trait, true)
-#include "clang/Basic/TransformTypeTraits.def"

[clang] [clang] Track function template instantiation from definition (PR #110387)

2024-10-08 Thread Matheus Izvekov via cfe-commits

https://github.com/mizvekov updated 
https://github.com/llvm/llvm-project/pull/110387

>From 28e582bc3b3058aa5ba946c9eb9b3d0e989b5c28 Mon Sep 17 00:00:00 2001
From: Matheus Izvekov 
Date: Sat, 28 Sep 2024 14:28:58 -0300
Subject: [PATCH] [clang] Track function template instantiation from definition

This fixes instantiation of definition for friend function templates,
when the declaration found and the one containing the definition
have different template contexts.

In these cases, the the function declaration corresponding to the
definition is not available; it may not even be instantiated at all.

So this patch adds a bit which tracks which function template
declaration was instantiated from the member template.
It's used to find which primary template serves as a context
for the purpose of obtainining the template arguments needed
to instantiate the definition.

Fixes #55509
---
 clang/docs/ReleaseNotes.rst   |   1 +
 clang/include/clang/AST/Decl.h|   7 ++
 clang/include/clang/AST/DeclBase.h|  10 +-
 clang/include/clang/AST/DeclTemplate.h|   9 ++
 clang/include/clang/Sema/Sema.h   |   6 ++
 clang/lib/AST/Decl.cpp|   1 +
 clang/lib/Sema/SemaTemplateDeduction.cpp  |  17 +--
 clang/lib/Sema/SemaTemplateInstantiate.cpp|  17 ++-
 .../lib/Sema/SemaTemplateInstantiateDecl.cpp  |  22 +++-
 clang/lib/Serialization/ASTReaderDecl.cpp |   1 +
 clang/lib/Serialization/ASTWriterDecl.cpp |   3 +-
 clang/test/SemaTemplate/GH55509.cpp   | 101 ++
 12 files changed, 169 insertions(+), 26 deletions(-)
 create mode 100644 clang/test/SemaTemplate/GH55509.cpp

diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index bd86fff6dd03fa..37b892c4e1655c 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -472,6 +472,7 @@ Bug Fixes to C++ Support
 - Fixed an assertion failure in debug mode, and potential crashes in release 
mode, when
   diagnosing a failed cast caused indirectly by a failed implicit conversion 
to the type of the constructor parameter.
 - Fixed an assertion failure by adjusting integral to boolean vector 
conversions (#GH108326)
+- Clang is now better at keeping track of friend function template instance 
contexts. (#GH55509)
 - Fixed an issue deducing non-type template arguments of reference type. 
(#GH73460)
 - Fixed an issue in constraint evaluation, where type constraints on the 
lambda expression
   containing outer unexpanded parameters were not correctly expanded. 
(#GH101754)
diff --git a/clang/include/clang/AST/Decl.h b/clang/include/clang/AST/Decl.h
index 7ff35d73df5997..6afc86710a8137 100644
--- a/clang/include/clang/AST/Decl.h
+++ b/clang/include/clang/AST/Decl.h
@@ -2299,6 +2299,13 @@ class FunctionDecl : public DeclaratorDecl,
 FunctionDeclBits.IsLateTemplateParsed = ILT;
   }
 
+  bool isInstantiatedFromMemberTemplate() const {
+return FunctionDeclBits.IsInstantiatedFromMemberTemplate;
+  }
+  void setInstantiatedFromMemberTemplate(bool Val = true) {
+FunctionDeclBits.IsInstantiatedFromMemberTemplate = Val;
+  }
+
   /// Whether this function is "trivial" in some specialized C++ senses.
   /// Can only be true for default constructors, copy constructors,
   /// copy assignment operators, and destructors.  Not meaningful until
diff --git a/clang/include/clang/AST/DeclBase.h 
b/clang/include/clang/AST/DeclBase.h
index ee662ed73d7e0e..eb67dc03157e64 100644
--- a/clang/include/clang/AST/DeclBase.h
+++ b/clang/include/clang/AST/DeclBase.h
@@ -1763,6 +1763,8 @@ class DeclContext {
 uint64_t HasImplicitReturnZero : 1;
 LLVM_PREFERRED_TYPE(bool)
 uint64_t IsLateTemplateParsed : 1;
+LLVM_PREFERRED_TYPE(bool)
+uint64_t IsInstantiatedFromMemberTemplate : 1;
 
 /// Kind of contexpr specifier as defined by ConstexprSpecKind.
 LLVM_PREFERRED_TYPE(ConstexprSpecKind)
@@ -1813,7 +1815,7 @@ class DeclContext {
   };
 
   /// Number of inherited and non-inherited bits in FunctionDeclBitfields.
-  enum { NumFunctionDeclBits = NumDeclContextBits + 31 };
+  enum { NumFunctionDeclBits = NumDeclContextBits + 32 };
 
   /// Stores the bits used by CXXConstructorDecl. If modified
   /// NumCXXConstructorDeclBits and the accessor
@@ -1824,12 +1826,12 @@ class DeclContext {
 LLVM_PREFERRED_TYPE(FunctionDeclBitfields)
 uint64_t : NumFunctionDeclBits;
 
-/// 20 bits to fit in the remaining available space.
+/// 19 bits to fit in the remaining available space.
 /// Note that this makes CXXConstructorDeclBitfields take
 /// exactly 64 bits and thus the width of NumCtorInitializers
 /// will need to be shrunk if some bit is added to NumDeclContextBitfields,
 /// NumFunctionDeclBitfields or CXXConstructorDeclBitfields.
-uint64_t NumCtorInitializers : 17;
+uint64_t NumCtorInitializers : 16;
 LLVM_PREFERRED_TYPE(bool)
 uint64_t IsInheritingConstructor : 1;
 
@@ -1843,7 +1845,7 @@

[clang-tools-extra] [llvm] [llvm] add support for mustache templating language (PR #105893)

2024-10-08 Thread via cfe-commits


@@ -0,0 +1,190 @@
+//===--- Mustache.h -*- C++ 
-*-===//
+//
+// 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
+//
+//===--===//
+//
+// Implementation of the Mustache templating language supports version 1.4.2
+// currently relies on llvm::json::Value for data input
+// see the Mustache spec for more information
+// (https://mustache.github.io/mustache.5.html).
+//
+// Current Features Supported:
+// - Variables
+// - Sections
+// - Inverted Sections
+// - Partials
+// - Comments
+// - Lambdas
+// - Unescaped Variables
+//
+// Features Not Supported:
+// - Set Delimiter
+// - Blocks
+// - Parents
+// - Dynamic Names
+//
+// The Template class is container class outputs the Mustache template string
+// and is main class for users. It stores all the lambdas and the ASTNode Tree.
+// When the Template is instantiated it tokenize the Template String and
+// creates a vector of Tokens. Then it calls a basic recursive descent parser
+// to construct the ASTNode Tree. The ASTNodes are all stored in an arena
+// allocator which is freed once the template class goes out of scope
+//
+// Usage:
+// \code
+//   // Creating a simple template and rendering it
+//   auto Template = Template("Hello, {{name}}!");
+//   Value Data = {{"name", "World"}};
+//   StringRef Rendered = Template.render(Data);
+//   // Rendered == "Hello, World!"
+//
+//   // Creating a template with a partial and rendering it
+//   auto Template = Template("{{>partial}}");
+//   Template.registerPartial("partial", "Hello, {{name}}!");
+//   Value Data = {{"name", "World"}};
+//   StringRef Rendered = Template.render(Data);
+//   // Rendered == "Hello, World!"
+//
+//   // Creating a template with a lambda and rendering it
+//   auto Template = Template("{{#lambda}}Hello, {{name}}!{{/lambda}}");
+//   Template.registerLambda("lambda", []() { return true; });
+//   Value Data = {{"name", "World"}};
+//   StringRef Rendered = Template.render(Data);
+//   // Rendered == "Hello, World!"
+// \endcode
+//===--===//
+
+#ifndef LLVM_SUPPORT_MUSTACHE
+#define LLVM_SUPPORT_MUSTACHE
+
+#include "Error.h"
+#include "llvm/ADT/StringMap.h"
+#include "llvm/Support/Allocator.h"
+#include "llvm/Support/JSON.h"
+#include 
+
+namespace llvm {
+namespace mustache {
+
+using Accessor = SmallVector>;
+using Lambda = std::function;
+using SectionLambda = std::function;
+
+class Token {
+public:
+  enum class Type {
+Text,
+Variable,
+Partial,
+SectionOpen,
+SectionClose,
+InvertSectionOpen,
+UnescapeVariable,
+Comment,
+  };
+
+  Token(StringRef Str);
+
+  Token(StringRef RawBody, StringRef Str, char Identifier);
+
+  StringRef getTokenBody() const { return TokenBody; };
+
+  StringRef getRawBody() const { return RawBody; };
+
+  void setTokenBody(SmallString<128> NewBody) { TokenBody = NewBody; };
+
+  Accessor getAccessor() const { return Accessor; };
+
+  Type getType() const { return TokenType; };
+
+  static Type getTokenType(char Identifier);
+
+private:
+  Type TokenType;
+  SmallString<128> RawBody;
+  Accessor Accessor;
+  SmallString<128> TokenBody;
+};
+
+class ASTNode {
+public:
+  enum Type {
+Root,
+Text,
+Partial,
+Variable,
+UnescapeVariable,
+Section,
+InvertSection,
+  };
+
+  ASTNode() : T(Type::Root), LocalContext(nullptr) {};
+
+  ASTNode(StringRef Body, ASTNode *Parent)
+  : T(Type::Text), Body(Body), Parent(Parent), LocalContext(nullptr) {};
+
+  // Constructor for Section/InvertSection/Variable/UnescapeVariable
+  ASTNode(Type T, Accessor Accessor, ASTNode *Parent)
+  : T(T), Parent(Parent), Children({}), Accessor(Accessor),
+LocalContext(nullptr) {};
+
+  void addChild(ASTNode *Child) { Children.emplace_back(Child); };
+
+  SmallString<128> getBody() const { return Body; };
+
+  void setBody(StringRef NewBody) { Body = NewBody; };
+
+  void setRawBody(StringRef NewBody) { RawBody = NewBody; };
+
+  SmallString<128> render(llvm::json::Value Data,
+  llvm::BumpPtrAllocator &Allocator,
+  DenseMap &Partials,
+  DenseMap &Lambdas,
+  DenseMap &SectionLambdas,
+  DenseMap &Escapes);
+
+private:
+  llvm::json::Value findContext();
+  Type T;
+  SmallString<128> RawBody;
+  SmallString<128> Body;
+  ASTNode *Parent;
+  std::vector Children;
+  const Accessor Accessor;
+  llvm::json::Value LocalContext;
+};
+
+// A Template represents the container for the AST and the partials
+// and Lambdas that are registered with it.
+class Template {
+public:
+  Template(StringRef TemplateStr);
+
+  SmallString<128> render(ll

[clang] [llvm] Update llvm::Registry to work for LLVM shared library builds on windows (PR #109024)

2024-10-08 Thread Aaron Ballman via cfe-commits

https://github.com/AaronBallman commented:

These changes LGTM but precommit CI was unable to run, so it would be nice if 
that could be re-run to ensure it comes back green before landing.

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


[clang] [clang] Track function template instantiation from definition (PR #110387)

2024-10-08 Thread Matheus Izvekov via cfe-commits

mizvekov wrote:

Now this is rebased on top of the `getTemplateInstantiationArgs` refactoring.

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


[clang] Make PCH's respect any VFS specified. (PR #106577)

2024-10-08 Thread Henrik Karlsson via cfe-commits

honkstar1 wrote:

I'm working with Neil and I've just tried changing our system to work the way 
where all our rsp etc use virtual paths and then create a vfsoverlay that 
points to the "right" places... it almost works for portable pch.

What is not working is "#include_next".. that gets resolved to a non-virtual 
path which is written into the .pch and .d files. For example this file: 
Unix\LibCxx\include\c++\v1\stddef.h has "#include_next "

Are there any options to control that?


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


[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)

2024-10-08 Thread Farzon Lotfi via cfe-commits


@@ -428,6 +431,7 @@ bool SPIRVInstructionSelector::spvSelect(Register ResVReg,
 
   case TargetOpcode::G_INTRINSIC:
   case TargetOpcode::G_INTRINSIC_W_SIDE_EFFECTS:
+  case TargetOpcode::G_INTRINSIC_CONVERGENT:

farzonl wrote:

Is there anything that distinguishes a `G_INTRINSIC_CONVERGENT` vs a 
`G_INTRINSIC`?  Seems like we are handling them the same way so wondering what 
happens with that extra information about convergence?


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


[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)

2024-10-08 Thread Farzon Lotfi via cfe-commits

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

LGTM

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


[clang] [llvm] [clang-format] Add CI check confirming ClangFormatStyleOptions.rst is up-to-date. (PR #111513)

2024-10-08 Thread Aiden Grossman via cfe-commits

https://github.com/boomanaiden154 requested changes to this pull request.

The documentation build workflow is not really the correct place to put this.

Also, why can't we just run the python script as part of building the docs 
instead of committing the result of the script to the repository?

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


[clang] [SystemZ][z/OS] Add z/OS customization file (PR #111182)

2024-10-08 Thread Abhina Sree via cfe-commits

https://github.com/abhina-sree approved this pull request.

LGTM

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


[clang] [llvm] [InstrPGO] Instrument sampling profile based cold function (PR #109837)

2024-10-08 Thread Ellis Hoag via cfe-commits


@@ -1119,6 +1125,18 @@ 
PassBuilder::buildModuleSimplificationPipeline(OptimizationLevel Level,
   // removed.
   MPM.addPass(
   PGOIndirectCallPromotion(true /* IsInLTO */, true /* SamplePGO */));
+
+if (InstrumentSampleColdFuncPath.getNumOccurrences() &&
+Phase != ThinOrFullLTOPhase::ThinLTOPostLink) {
+  assert(!InstrumentSampleColdFuncPath.empty() &&
+ "File path is requeired for instrumentation generation");
+  InstrumentColdFunctionCoverage = true;
+  addPreInlinerPasses(MPM, Level, Phase);
+  addPGOInstrPasses(MPM, Level, /* RunProfileGen */ true,
+/* IsCS */ false, /* AtomicCounterUpdate */ false,
+InstrumentSampleColdFuncPath, "",
+IntrusiveRefCntPtr());
+}

ellishg wrote:

> if a function symbol shows in the binary but not in the profile, we can treat 
> it as cold function(set 0 entry count)

I wasn't aware that SamplePGO did this. This is indeed different than IRPGO. 
Perhaps it makes more sense to use a separate flag to control this case. Maybe 
something like 
`-instrument-cold-function-coverage-mode={optimistic,conservative}` where 
`optimistic` means we optimistically treat unprofiled functions as cold and 
`conservative` means we conservatively assume unprofiled functions is hot. 

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


[clang-tools-extra] a199fb1 - [clang-tidy] Only expand macros in modernize-use-std-format/print (#97911)

2024-10-08 Thread via cfe-commits

Author: Mike Crowe
Date: 2024-10-08T22:03:58+02:00
New Revision: a199fb1229987d0885a4367e3a439db336069156

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

LOG: [clang-tidy] Only expand  macros in 
modernize-use-std-format/print (#97911)

Expanding all macros in the printf/absl::StrFormat format string before
conversion could easily break code if those macros are expanded change
their definition between builds. It's important for this check to expand
the  PRI macros though, so let's ensure that the presence of
any other macros in the format string causes the check to emit a warning
and not perform any conversion.

Added: 


Modified: 
clang-tools-extra/clang-tidy/modernize/UseStdFormatCheck.cpp
clang-tools-extra/clang-tidy/modernize/UseStdFormatCheck.h
clang-tools-extra/clang-tidy/modernize/UseStdPrintCheck.cpp
clang-tools-extra/clang-tidy/modernize/UseStdPrintCheck.h
clang-tools-extra/clang-tidy/utils/FormatStringConverter.cpp
clang-tools-extra/clang-tidy/utils/FormatStringConverter.h
clang-tools-extra/docs/ReleaseNotes.rst
clang-tools-extra/docs/clang-tidy/checks/modernize/use-std-format.rst
clang-tools-extra/docs/clang-tidy/checks/modernize/use-std-print.rst
clang-tools-extra/test/clang-tidy/checkers/Inputs/Headers/inttypes.h
clang-tools-extra/test/clang-tidy/checkers/modernize/use-std-format.cpp
clang-tools-extra/test/clang-tidy/checkers/modernize/use-std-print.cpp

Removed: 




diff  --git a/clang-tools-extra/clang-tidy/modernize/UseStdFormatCheck.cpp 
b/clang-tools-extra/clang-tidy/modernize/UseStdFormatCheck.cpp
index cdb34aef1b0e61..f97b844c564961 100644
--- a/clang-tools-extra/clang-tidy/modernize/UseStdFormatCheck.cpp
+++ b/clang-tools-extra/clang-tidy/modernize/UseStdFormatCheck.cpp
@@ -44,6 +44,7 @@ void UseStdFormatCheck::registerPPCallbacks(const 
SourceManager &SM,
 Preprocessor *PP,
 Preprocessor *ModuleExpanderPP) {
   IncludeInserter.registerPreprocessor(PP);
+  this->PP = PP;
 }
 
 void UseStdFormatCheck::registerMatchers(MatchFinder *Finder) {
@@ -75,9 +76,9 @@ void UseStdFormatCheck::check(const MatchFinder::MatchResult 
&Result) {
 
   utils::FormatStringConverter::Configuration ConverterConfig;
   ConverterConfig.StrictMode = StrictMode;
-  utils::FormatStringConverter Converter(Result.Context, StrFormat,
- FormatArgOffset, ConverterConfig,
- getLangOpts());
+  utils::FormatStringConverter Converter(
+  Result.Context, StrFormat, FormatArgOffset, ConverterConfig,
+  getLangOpts(), *Result.SourceManager, *PP);
   const Expr *StrFormatCall = StrFormat->getCallee();
   if (!Converter.canApply()) {
 diag(StrFormat->getBeginLoc(),

diff  --git a/clang-tools-extra/clang-tidy/modernize/UseStdFormatCheck.h 
b/clang-tools-extra/clang-tidy/modernize/UseStdFormatCheck.h
index b59a4708c6e4bc..9ac2240212ebf6 100644
--- a/clang-tools-extra/clang-tidy/modernize/UseStdFormatCheck.h
+++ b/clang-tools-extra/clang-tidy/modernize/UseStdFormatCheck.h
@@ -44,6 +44,7 @@ class UseStdFormatCheck : public ClangTidyCheck {
   StringRef ReplacementFormatFunction;
   utils::IncludeInserter IncludeInserter;
   std::optional MaybeHeaderToInclude;
+  Preprocessor *PP = nullptr;
 };
 
 } // namespace clang::tidy::modernize

diff  --git a/clang-tools-extra/clang-tidy/modernize/UseStdPrintCheck.cpp 
b/clang-tools-extra/clang-tidy/modernize/UseStdPrintCheck.cpp
index 16f2f4b3e7d1af..9161c0e702a28c 100644
--- a/clang-tools-extra/clang-tidy/modernize/UseStdPrintCheck.cpp
+++ b/clang-tools-extra/clang-tidy/modernize/UseStdPrintCheck.cpp
@@ -68,6 +68,7 @@ void UseStdPrintCheck::registerPPCallbacks(const 
SourceManager &SM,
Preprocessor *PP,
Preprocessor *ModuleExpanderPP) {
   IncludeInserter.registerPreprocessor(PP);
+  this->PP = PP;
 }
 
 static clang::ast_matchers::StatementMatcher
@@ -131,7 +132,8 @@ void UseStdPrintCheck::check(const MatchFinder::MatchResult 
&Result) {
   ConverterConfig.StrictMode = StrictMode;
   ConverterConfig.AllowTrailingNewlineRemoval = true;
   utils::FormatStringConverter Converter(
-  Result.Context, Printf, FormatArgOffset, ConverterConfig, getLangOpts());
+  Result.Context, Printf, FormatArgOffset, ConverterConfig, getLangOpts(),
+  *Result.SourceManager, *PP);
   const Expr *PrintfCall = Printf->getCallee();
   const StringRef ReplacementFunction = Converter.usePrintNewlineFunction()
 ? ReplacementPrintlnFunction

diff  --git a/clang-tools-extra/clang-tidy/modernize/UseStdPrintCheck.h 
b/clang-to

[clang-tools-extra] [clang-tidy] Only expand macros in modernize-use-std-format/print (PR #97911)

2024-10-08 Thread Julian Schmidt via cfe-commits

5chmidti wrote:

Yep, thanks. Sorry for the delay

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


[clang-tools-extra] [clang-tidy] Only expand macros in modernize-use-std-format/print (PR #97911)

2024-10-08 Thread Julian Schmidt via cfe-commits

https://github.com/5chmidti closed 
https://github.com/llvm/llvm-project/pull/97911
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Allow `ConditionalOperator` fast-math flags to be overridden by `pragma float_control` (PR #105912)

2024-10-08 Thread Andy Kaylor via cfe-commits

andykaylor wrote:

@rjmccall I understand your point, and I think you're raising a good question. 
Let's walk through an example that illustrates why we currently want FMF on 
phis and selects and see if we can agree on an alternative way to handle it. In 
a comment on https://github.com/llvm/llvm-project/issues/51601, I started with 
this:

```
double floatingAbs(double x) {
  return (x < 0) ? -x : x;
}

```
We want to optimize that to `llvm.fabs(x)`, but we can only do that if we don't 
care about the sign of zero. I walked through the steps of how that happens 
[here](https://github.com/llvm/llvm-project/issues/51601#issuecomment-981047527),
 but let me jump to the optimized IR just before the replacement happens 
because that's sufficient for the discussion about FMF on select instructions. 
The optimizer reduces the IR to this:

```
define dso_local double @floatingAbs(double %0) {
  %2 = fcmp fast olt double %0, 0.00e+00
  %3 = fneg fast double %0
  %4 = select fast i1 %2, double %3, double %0
  ret double %4
}
```
We need the `nsz` flag to turn this into `llvm.fabs(x)`. The `nsz` flag is 
present on the `fcmp` instruction, but that doesn't matter because `0.0` 
compares as equal to `-0.0` with or without the flag. We also have `nsz` on the 
`fneg` instruction, but again that doesn't matter because we don't hit the 
`fneg` instruction for `0.0` or `-0.0`. We want this sequence to produce the 
absolute value of `x` but the only way we can say that it does is if we don't 
care about the sign of zero on the `select` instruction.

If this code is called with `x == -0.0`, the `select` instruction will return 
-0.0. We can only replace this with `llvm.fabs(x)` if we know we are allowed to 
ignore the sign of zero for the whole pattern. That leaves us two choices: 
either we depend on a function attribute saying that we can ignore the sign of 
zero for the entire function, or we must have the `nsz` flag set on all 
instructions involved in the pattern.

As I said before, relying on the function attribute gives us correct results, 
but because functions can have mixed fast-math states (through either inlining 
or pragmas), we may lose an optimization here. To me, it seems that having 
fast-math flags on `select` instruction is easiest way to do this without 
potentially losing optimizations, and that indirectly implies that we'd like to 
have FMF on phis and loads. Currently, we're in a mixed state in that regard 
where we accept the loss of optimization if a load is involved but preserve 
optimization through phis and selects.

However, as I think about this it occurs to me that there is another 
possibility. The argument about only applies to the `nsz` flag. The `nnan` and 
`ninf` flags can be deduced, and the rewrite flags don't have any meaning for 
phis, loads, and selects. Perhaps we shouldn't be looking at the `select` 
instruction but instead should be looking for the `nsz` flag on the uses of the 
select instruction. In the trivial case I cited above, the result of the select 
is being returned, so looking at the function attribute is correct. If the 
value selected were being used in the function, we would look at the uses. If 
all of the uses have the `nsz` flag set, This would complicate the handling a 
bit, but it certainly seems to make more sense in terms of the semantics of the 
`nsz` flag.

Tagging @jcranmer-intel who has been working on clarifying FMF semantics.

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


[clang] [clang] assume_aligned incorrectly diagnoses a dependent return type (PR #111573)

2024-10-08 Thread Amr Hesham via cfe-commits

https://github.com/AmrDeveloper updated 
https://github.com/llvm/llvm-project/pull/111573

>From dea97ae4f893774489bfd423e9536e486f022bb9 Mon Sep 17 00:00:00 2001
From: AmrDeveloper 
Date: Tue, 8 Oct 2024 20:12:45 +0200
Subject: [PATCH] [clang] assume_aligned incorrectly diagnoses a dependent
 return type

---
 clang/include/clang/Sema/Sema.h| 6 +++---
 clang/lib/Sema/SemaDeclAttr.cpp| 7 ---
 clang/test/SemaCXX/builtin-assume-aligned-tmpl.cpp | 6 ++
 clang/test/SemaObjCXX/noescape.mm  | 2 +-
 4 files changed, 14 insertions(+), 7 deletions(-)

diff --git a/clang/include/clang/Sema/Sema.h b/clang/include/clang/Sema/Sema.h
index 7ff9c2754a6fe0..3a5bd3be43ee64 100644
--- a/clang/include/clang/Sema/Sema.h
+++ b/clang/include/clang/Sema/Sema.h
@@ -4453,9 +4453,9 @@ class Sema final : public SemaBase {
   SourceLocation *ArgLocation = nullptr);
 
   /// Determine if type T is a valid subject for a nonnull and similar
-  /// attributes. By default, we look through references (the behavior used by
-  /// nonnull), but if the second parameter is true, then we treat a reference
-  /// type as valid.
+  /// attributes. We skip dependence By default, we look through references
+  /// (the behavior used by nonnull), but if the second parameter is true, then
+  /// we treat a reference type as valid..
   bool isValidPointerAttrType(QualType T, bool RefOkay = false);
 
   /// AddAssumeAlignedAttr - Adds an assume_aligned attribute to a particular
diff --git a/clang/lib/Sema/SemaDeclAttr.cpp b/clang/lib/Sema/SemaDeclAttr.cpp
index af983349a89b58..e2174ba926f17f 100644
--- a/clang/lib/Sema/SemaDeclAttr.cpp
+++ b/clang/lib/Sema/SemaDeclAttr.cpp
@@ -1216,6 +1216,8 @@ static void handlePreferredName(Sema &S, Decl *D, const 
ParsedAttr &AL) {
 }
 
 bool Sema::isValidPointerAttrType(QualType T, bool RefOkay) {
+  if (T->isDependentType())
+return true;
   if (RefOkay) {
 if (T->isReferenceType())
   return true;
@@ -1284,7 +1286,7 @@ static void handleNonNullAttr(Sema &S, Decl *D, const 
ParsedAttr &AL) {
 for (unsigned I = 0, E = getFunctionOrMethodNumParams(D);
  I != E && !AnyPointers; ++I) {
   QualType T = getFunctionOrMethodParamType(D, I);
-  if (T->isDependentType() || S.isValidPointerAttrType(T))
+  if (S.isValidPointerAttrType(T))
 AnyPointers = true;
 }
 
@@ -1409,8 +1411,7 @@ void Sema::AddAllocAlignAttr(Decl *D, const 
AttributeCommonInfo &CI,
   AllocAlignAttr TmpAttr(Context, CI, ParamIdx());
   SourceLocation AttrLoc = CI.getLoc();
 
-  if (!ResultType->isDependentType() &&
-  !isValidPointerAttrType(ResultType, /* RefOkay */ true)) {
+  if (!isValidPointerAttrType(ResultType, /* RefOkay */ true)) {
 Diag(AttrLoc, diag::warn_attribute_return_pointers_refs_only)
 << &TmpAttr << CI.getRange() << 
getFunctionOrMethodResultSourceRange(D);
 return;
diff --git a/clang/test/SemaCXX/builtin-assume-aligned-tmpl.cpp 
b/clang/test/SemaCXX/builtin-assume-aligned-tmpl.cpp
index 61b85557d6b294..e709c936735c74 100644
--- a/clang/test/SemaCXX/builtin-assume-aligned-tmpl.cpp
+++ b/clang/test/SemaCXX/builtin-assume-aligned-tmpl.cpp
@@ -52,6 +52,12 @@ T *atest3() __attribute__((assume_aligned(31, o))); // 
expected-error {{requeste
 template 
 T *atest4() __attribute__((assume_aligned(32, o)));
 
+template
+T atest5(int) __attribute__((assume_aligned(2)));
+
+// expected-warning@+1 {{'assume_aligned' attribute only applies to return 
values that are pointers or references}}
+int atest6(int) __attribute__((assume_aligned(2)));
+
 void test22() {
   atest3();
   atest4();
diff --git a/clang/test/SemaObjCXX/noescape.mm 
b/clang/test/SemaObjCXX/noescape.mm
index 4b52164dffd3da..cdcad07feb2bc8 100644
--- a/clang/test/SemaObjCXX/noescape.mm
+++ b/clang/test/SemaObjCXX/noescape.mm
@@ -17,7 +17,7 @@
 void noescapeFunc2(int *); // expected-error {{conflicting types for 
'noescapeFunc2'}}
 
 template 
-void noescapeFunc5(__attribute__((noescape)) T); // expected-warning 
{{'noescape' attribute only applies to pointer arguments}}
+void noescapeFunc5(__attribute__((noescape)) T);
 template 
 void noescapeFunc6(__attribute__((noescape)) const T &);
 template 

___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [HLSL] Make HLSLAttributedResourceType canonical and add code paths to convert HLSL types to DirectX target types (PR #110327)

2024-10-08 Thread Chris B via cfe-commits


@@ -3437,6 +3437,9 @@ static void encodeTypeForFunctionPointerAuth(const 
ASTContext &Ctx,
 OS << II->getLength() << II->getName();
 return;
   }
+  case Type::HLSLAttributedResource:

llvm-beanz wrote:

This should maybe be higher up with the "should never get here" because I don't 
think we'll be supporting authenticated pointers for this.

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


[clang] [HLSL] Make HLSLAttributedResourceType canonical and add code paths to convert HLSL types to DirectX target types (PR #110327)

2024-10-08 Thread Chris B via cfe-commits


@@ -3943,6 +3943,9 @@ void ItaniumRTTIBuilder::BuildVTablePointer(const Type 
*Ty) {
 // abi::__pointer_to_member_type_info.
 VTableName = "_ZTVN10__cxxabiv129__pointer_to_member_type_infoE";
 break;
+
+  case Type::HLSLAttributedResource:
+llvm_unreachable("not yet implemented");

llvm-beanz wrote:

I suspect we should probably make this more of an "HLSL doesn't support virtual 
functions".

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


[clang] [HLSL] Make HLSLAttributedResourceType canonical and add code paths to convert HLSL types to DirectX target types (PR #110327)

2024-10-08 Thread Chris B via cfe-commits


@@ -4205,6 +4208,9 @@ llvm::Constant *ItaniumRTTIBuilder::BuildTypeInfo(
   case Type::Atomic:
 // No fields, at least for the moment.
 break;
+
+  case Type::HLSLAttributedResource:
+llvm_unreachable("not yet implemented");

llvm-beanz wrote:

This too should probably be "HLSL doesn't support RTTI".

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


[clang] [HLSL] Make HLSLAttributedResourceType canonical and add code paths to convert HLSL types to DirectX target types (PR #110327)

2024-10-08 Thread Chris B via cfe-commits

https://github.com/llvm-beanz commented:

A few (mostly small) comments

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


[clang] [HLSL] Make HLSLAttributedResourceType canonical and add code paths to convert HLSL types to DirectX target types (PR #110327)

2024-10-08 Thread Chris B via cfe-commits


@@ -13672,6 +13690,9 @@ static QualType getCommonNonSugarTypeNode(ASTContext 
&Ctx, const Type *X,
 TX->getDepth(), TX->getIndex(), TX->isParameterPack(),
 getCommonDecl(TX->getDecl(), TY->getDecl()));
   }
+  case Type::HLSLAttributedResource: {

llvm-beanz wrote:

Do we expect these types to be sugared? It seems like we should maybe make 
these "sugar-free" above? The only case I can think of where we might have 
sugar would be if the component type was sugared... not sure.

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


[clang] [HLSL] Make HLSLAttributedResourceType canonical and add code paths to convert HLSL types to DirectX target types (PR #110327)

2024-10-08 Thread Chris B via cfe-commits


@@ -29,19 +29,40 @@ class DirectXTargetCodeGenInfo : public TargetCodeGenInfo {
 
 llvm::Type *DirectXTargetCodeGenInfo::getHLSLType(CodeGenModule &CGM,
   const Type *Ty) const {
-  auto *BuiltinTy = dyn_cast(Ty);
-  if (!BuiltinTy || BuiltinTy->getKind() != BuiltinType::HLSLResource)
+  auto *ResType = dyn_cast(Ty);
+  if (!ResType)
 return nullptr;
 
   llvm::LLVMContext &Ctx = CGM.getLLVMContext();
-  // FIXME: translate __hlsl_resource_t to target("dx.TypedBuffer", <4 x 
float>,
-  // 1, 0, 0) only for now (RWBuffer); more work us needed to determine
-  // the target ext type and its parameters based on the handle type
-  // attributes (not yet implemented)
-  llvm::FixedVectorType *ElemType =
-  llvm::FixedVectorType::get(llvm::Type::getFloatTy(Ctx), 4);
-  unsigned Flags[] = {/*IsWriteable*/ 1, /*IsROV*/ 0, /*IsSigned*/ 0};
-  return llvm::TargetExtType::get(Ctx, "dx.TypedBuffer", {ElemType}, Flags);
+  const HLSLAttributedResourceType::Attributes &ResAttrs = ResType->getAttrs();
+  switch (ResAttrs.ResourceClass) {
+  case llvm::dxil::ResourceClass::UAV:
+  case llvm::dxil::ResourceClass::SRV: {
+// TypedBuffer and RawBuffer both need element type
+QualType ContainedTy = ResType->getContainedType();
+if (ContainedTy.isNull())
+  return nullptr;
+
+// convert element type
+llvm::Type *ElemType = CGM.getTypes().ConvertType(ContainedTy);
+
+const char *TypeName =

llvm-beanz wrote:

nit:
```suggestion
llvm::StringRef TypeName =
```

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


[libcxx] [libcxxabi] [libunwind] [runtimes] Always define cxx_shared, cxx_static & other targets (PR #80007)

2024-10-08 Thread Louis Dionne via cfe-commits

https://github.com/ldionne updated 
https://github.com/llvm/llvm-project/pull/80007

>From 447159a21d73d6b4b5c6f6c4710231f01e0af4fc Mon Sep 17 00:00:00 2001
From: Louis Dionne 
Date: Wed, 12 Oct 2022 18:06:32 -0400
Subject: [PATCH] [runtimes] Always define cxx_shared, cxx_static & other
 targets

However, mark them as EXCLUDE_FROM_ALL when we don't want to build them.
Simply declaring the targets should be of no harm, and it allows other
projects to mention these targets regardless of whether they end up
being built or not.

This patch basically moves the definition of e.g. cxx_shared out of
the `if (LIBCXX_ENABLE_SHARED)` and instead marks it as EXCLUDE_FROM_ALL
conditionally on whether LIBCXX_ENABLE_SHARED is passed. It then does the
same for libunwind and libc++abi targets.

This is a reapplication of 79ee0342dbf0, which was reverted in a3539090884c
because it broke the TSAN and the Fuchsia builds.

Resolves #77654

Differential Revision: https://reviews.llvm.org/D134221
---
 libcxx/cmake/caches/AIX.cmake |  7 +++
 libcxx/cmake/caches/Armv7M-picolibc.cmake | 11 +++
 libcxx/src/CMakeLists.txt | 22 +++---
 libcxxabi/src/CMakeLists.txt  | 20 +++-
 libunwind/src/CMakeLists.txt  | 18 ++
 5 files changed, 50 insertions(+), 28 deletions(-)

diff --git a/libcxx/cmake/caches/AIX.cmake b/libcxx/cmake/caches/AIX.cmake
index 4ec78f9bbd5923..036fdfdae60725 100644
--- a/libcxx/cmake/caches/AIX.cmake
+++ b/libcxx/cmake/caches/AIX.cmake
@@ -16,3 +16,10 @@ set(LIBCXX_CXX_ABI libcxxabi CACHE STRING "")
 set(LIBUNWIND_ENABLE_SHARED ON CACHE BOOL "")
 set(LIBUNWIND_ENABLE_STATIC OFF CACHE BOOL "")
 set(LIBCXX_ABI_DEFINES "_LIBCPP_ABI_IOS_ALLOW_ARBITRARY_FILL_VALUE" CACHE 
STRING "")
+
+# On AIX, both shared and static libraries are archived. As a result, both the 
static and the shared targets end
+# up with a `.a` suffix, which conflict. To workaround that, we set a 
different output name for the static
+# libraries, which we never actually build anyway. For more information, see 
https://gitlab.kitware.com/cmake/cmake/-/issues/19494.
+set(LIBCXX_STATIC_OUTPUT_NAME "c++-static" CACHE STRING "")
+set(LIBCXXABI_STATIC_OUTPUT_NAME "c++abi-static" CACHE STRING "")
+set(LIBUNWIND_STATIC_OUTPUT_NAME "unwind-static" CACHE STRING "")
diff --git a/libcxx/cmake/caches/Armv7M-picolibc.cmake 
b/libcxx/cmake/caches/Armv7M-picolibc.cmake
index b5f9089308d22e..0f8189b457285e 100644
--- a/libcxx/cmake/caches/Armv7M-picolibc.cmake
+++ b/libcxx/cmake/caches/Armv7M-picolibc.cmake
@@ -39,3 +39,14 @@ set(LIBUNWIND_IS_BAREMETAL ON CACHE BOOL "")
 set(LIBUNWIND_REMEMBER_HEAP_ALLOC ON CACHE BOOL "")
 set(LIBUNWIND_USE_COMPILER_RT ON CACHE BOOL "")
 find_program(QEMU_SYSTEM_ARM qemu-system-arm REQUIRED)
+
+# On embedded platforms that don't support shared library targets, CMake 
implicitly changes shared
+# library targets to be static library targets. This results in duplicate 
definitions of the static
+# library targets even though we might not ever build the shared library 
target, which breaks the
+# build. To work around this, we change the output name of the  shared library 
target so that it
+# can't conflict with the static library target.
+#
+# This is tracked by https://gitlab.kitware.com/cmake/cmake/-/issues/25759.
+set(LIBCXX_SHARED_OUTPUT_NAME "c++-shared" CACHE STRING "")
+set(LIBCXXABI_SHARED_OUTPUT_NAME "c++abi-shared" CACHE STRING "")
+set(LIBUNWIND_SHARED_OUTPUT_NAME "unwind-shared" CACHE STRING "")
diff --git a/libcxx/src/CMakeLists.txt b/libcxx/src/CMakeLists.txt
index 806e341ba3b72f..3da598e40d4292 100644
--- a/libcxx/src/CMakeLists.txt
+++ b/libcxx/src/CMakeLists.txt
@@ -143,10 +143,6 @@ if (LIBCXX_ENABLE_NEW_DELETE_DEFINITIONS)
 )
 endif()
 
-if(NOT LIBCXX_INSTALL_LIBRARY)
-  set(exclude_from_all EXCLUDE_FROM_ALL)
-endif()
-
 if (APPLE AND LLVM_USE_SANITIZER)
   if (("${LLVM_USE_SANITIZER}" STREQUAL "Address") OR
   ("${LLVM_USE_SANITIZER}" STREQUAL "Address;Undefined") OR
@@ -177,13 +173,13 @@ split_list(LIBCXX_COMPILE_FLAGS)
 split_list(LIBCXX_LINK_FLAGS)
 
 # Build the shared library.
-if (LIBCXX_ENABLE_SHARED)
-  add_library(cxx_shared SHARED ${exclude_from_all} ${LIBCXX_SOURCES} 
${LIBCXX_HEADERS})
+  add_library(cxx_shared SHARED ${LIBCXX_SOURCES} ${LIBCXX_HEADERS})
   target_include_directories(cxx_shared PRIVATE ${CMAKE_CURRENT_SOURCE_DIR})
   target_link_libraries(cxx_shared PUBLIC cxx-headers libcxx-libc-shared
PRIVATE ${LIBCXX_LIBRARIES})
   set_target_properties(cxx_shared
 PROPERTIES
+  EXCLUDE_FROM_ALL "$,FALSE,TRUE>"
   COMPILE_FLAGS "${LIBCXX_COMPILE_FLAGS}"
   LINK_FLAGS"${LIBCXX_LINK_FLAGS}"
   OUTPUT_NAME   "${LIBCXX_SHARED_OUTPUT_NAME}"
@@ -251,7 +247,10 @@ if (LIBCXX_ENABLE_SHARED)
 )
   endif()
 
+if (LIBCXX_ENABLE_SHARED)
   list(APPEND LIBCXX_BUILD_TARGETS "cxx_shared")
+endif()
+
   if(WIN32 AND NOT MINGW AND NOT "${

[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)

2024-10-08 Thread Finn Plummer via cfe-commits


@@ -87,6 +87,7 @@ class CGHLSLRuntime {
   GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot)
   GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot)
   GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane)
+  GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, waveReadLaneAt)

inbelic wrote:

If we use `_` separated then the generated names will use `.` to separate them. 
So eg `wave_read_lane_at` becomes `llvm.dx.wave.read.lane.at`. Which we decided 
was quite confusing due to the confusion with a namespace. I will clean up the 
other intrinsic to cohere to this in a follow up pr.

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


[clang] [llvm] [InstrPGO] Instrument sampling profile based cold function (PR #109837)

2024-10-08 Thread Lei Wang via cfe-commits

https://github.com/wlei-llvm updated 
https://github.com/llvm/llvm-project/pull/109837

>From 07a2cab3fa5df2965f9f7da9ee2d3603581a47f1 Mon Sep 17 00:00:00 2001
From: wlei 
Date: Sun, 22 Sep 2024 20:23:20 -0700
Subject: [PATCH 1/5] [InstrPGO] Instrument sampling profile based cold
 function

---
 clang/include/clang/Driver/Options.td |  6 +
 clang/lib/Driver/ToolChain.cpp|  4 +++-
 clang/lib/Driver/ToolChains/Clang.cpp | 18 ++
 clang/test/CodeGen/Inputs/pgo-cold-func.prof  |  2 ++
 .../test/CodeGen/pgo-cold-function-coverage.c | 12 ++
 llvm/lib/Passes/PassBuilderPipelines.cpp  | 18 ++
 .../Instrumentation/PGOInstrumentation.cpp| 16 +
 .../PGOProfile/instr-gen-cold-function.ll | 24 +++
 8 files changed, 99 insertions(+), 1 deletion(-)
 create mode 100644 clang/test/CodeGen/Inputs/pgo-cold-func.prof
 create mode 100644 clang/test/CodeGen/pgo-cold-function-coverage.c
 create mode 100644 llvm/test/Transforms/PGOProfile/instr-gen-cold-function.ll

diff --git a/clang/include/clang/Driver/Options.td 
b/clang/include/clang/Driver/Options.td
index 002f60350543d9..6bb92427f2d53f 100644
--- a/clang/include/clang/Driver/Options.td
+++ b/clang/include/clang/Driver/Options.td
@@ -1784,6 +1784,12 @@ defm debug_info_for_profiling : 
BoolFOption<"debug-info-for-profiling",
   PosFlag,
   NegFlag>;
+def fprofile_generate_cold_function_coverage : Flag<["-"], 
"fprofile-generate-cold-function-coverage">, 
+Group, Visibility<[ClangOption, CLOption]>,
+HelpText<"Generate instrumented code to cold functions into 
default.profraw file (overridden by '=' form of option or LLVM_PROFILE_FILE env 
var)">;
+def fprofile_generate_cold_function_coverage_EQ : Joined<["-"], 
"fprofile-generate-cold-function-coverage=">, 
+Group, Visibility<[ClangOption, CLOption]>, 
MetaVarName<"">,
+HelpText<"Generate instrumented code to cold functions into 
/default.profraw (overridden by LLVM_PROFILE_FILE env var)">; 
 def fprofile_instr_generate : Flag<["-"], "fprofile-instr-generate">,
 Group, Visibility<[ClangOption, CLOption]>,
 HelpText<"Generate instrumented code to collect execution counts into 
default.profraw file (overridden by '=' form of option or LLVM_PROFILE_FILE env 
var)">;
diff --git a/clang/lib/Driver/ToolChain.cpp b/clang/lib/Driver/ToolChain.cpp
index 16f9b629fc538c..e56db150c6b47e 100644
--- a/clang/lib/Driver/ToolChain.cpp
+++ b/clang/lib/Driver/ToolChain.cpp
@@ -889,7 +889,9 @@ bool ToolChain::needsProfileRT(const ArgList &Args) {
  Args.hasArg(options::OPT_fprofile_instr_generate) ||
  Args.hasArg(options::OPT_fprofile_instr_generate_EQ) ||
  Args.hasArg(options::OPT_fcreate_profile) ||
- Args.hasArg(options::OPT_forder_file_instrumentation);
+ Args.hasArg(options::OPT_forder_file_instrumentation) ||
+ Args.hasArg(options::OPT_fprofile_generate_cold_function_coverage) ||
+ Args.hasArg(options::OPT_fprofile_generate_cold_function_coverage_EQ);
 }
 
 bool ToolChain::needsGCovInstrumentation(const llvm::opt::ArgList &Args) {
diff --git a/clang/lib/Driver/ToolChains/Clang.cpp 
b/clang/lib/Driver/ToolChains/Clang.cpp
index 0bab48caf1a5e2..00602a08232ba2 100644
--- a/clang/lib/Driver/ToolChains/Clang.cpp
+++ b/clang/lib/Driver/ToolChains/Clang.cpp
@@ -649,6 +649,24 @@ static void addPGOAndCoverageFlags(const ToolChain &TC, 
Compilation &C,
 }
   }
 
+  if (auto *ColdFuncCoverageArg = Args.getLastArg(
+  options::OPT_fprofile_generate_cold_function_coverage,
+  options::OPT_fprofile_generate_cold_function_coverage_EQ)) {
+SmallString<128> Path(
+ColdFuncCoverageArg->getOption().matches(
+options::OPT_fprofile_generate_cold_function_coverage_EQ)
+? ColdFuncCoverageArg->getValue()
+: "");
+llvm::sys::path::append(Path, "default_%m.profraw");
+CmdArgs.push_back("-mllvm");
+CmdArgs.push_back(Args.MakeArgString(
+Twine("--instrument-sample-cold-function-path=") + Path));
+CmdArgs.push_back("-mllvm");
+CmdArgs.push_back("--instrument-cold-function-coverage");
+CmdArgs.push_back("-mllvm");
+CmdArgs.push_back("--pgo-function-entry-coverage");
+  }
+
   Arg *PGOGenArg = nullptr;
   if (PGOGenerateArg) {
 assert(!CSPGOGenerateArg);
diff --git a/clang/test/CodeGen/Inputs/pgo-cold-func.prof 
b/clang/test/CodeGen/Inputs/pgo-cold-func.prof
new file mode 100644
index 00..e50be02e0a8545
--- /dev/null
+++ b/clang/test/CodeGen/Inputs/pgo-cold-func.prof
@@ -0,0 +1,2 @@
+foo:1:1
+ 1: 1
diff --git a/clang/test/CodeGen/pgo-cold-function-coverage.c 
b/clang/test/CodeGen/pgo-cold-function-coverage.c
new file mode 100644
index 00..0d2767c022b9f1
--- /dev/null
+++ b/clang/test/CodeGen/pgo-cold-function-coverage.c
@@ -0,0 +1,12 @@
+// Test -fprofile-generate-cold-function-coverage 
+// RUN: %clang -O2 -fprofile-generate-cold-function-coverage=/xxx

[clang] [llvm] [InstrPGO] Instrument sampling profile based cold function (PR #109837)

2024-10-08 Thread Lei Wang via cfe-commits


@@ -1119,6 +1125,18 @@ 
PassBuilder::buildModuleSimplificationPipeline(OptimizationLevel Level,
   // removed.
   MPM.addPass(
   PGOIndirectCallPromotion(true /* IsInLTO */, true /* SamplePGO */));
+
+if (InstrumentSampleColdFuncPath.getNumOccurrences() &&
+Phase != ThinOrFullLTOPhase::ThinLTOPostLink) {
+  assert(!InstrumentSampleColdFuncPath.empty() &&
+ "File path is requeired for instrumentation generation");
+  InstrumentColdFunctionCoverage = true;
+  addPreInlinerPasses(MPM, Level, Phase);
+  addPGOInstrPasses(MPM, Level, /* RunProfileGen */ true,
+/* IsCS */ false, /* AtomicCounterUpdate */ false,
+InstrumentSampleColdFuncPath, "",
+IntrusiveRefCntPtr());
+}

wlei-llvm wrote:

Good point, that's more flexible, thanks!

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


[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)

2024-10-08 Thread Finn Plummer via cfe-commits

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

>From 70089645ec5cf62b491a56df96ec46f4328fbc11 Mon Sep 17 00:00:00 2001
From: Finn Plummer 
Date: Thu, 3 Oct 2024 11:43:51 -0700
Subject: [PATCH 01/10] [HLSL] Implement `WaveReadLaneAt` intrinsic

- create a clang built-in in Builtins.td
- add semantic checking in SemaHLSL.cpp
- link the WaveReadLaneAt api in hlsl_intrinsics.h
- add lowering to spirv backend op GroupNonUniformShuffle
  with Scope = 2 (Group) in SPIRVInstructionSelector.cpp

- add tests for HLSL intrinsic lowering to spirv intrinsic in
  WaveReadLaneAt.hlsl
- add tests for sema checks in WaveReadLaneAt-errors.hlsl
- add spir-v backend tests in WaveReadLaneAt.ll
---
 clang/include/clang/Basic/Builtins.td |  6 +++
 clang/lib/CodeGen/CGBuiltin.cpp   | 16 
 clang/lib/CodeGen/CGHLSLRuntime.h |  1 +
 clang/lib/Headers/hlsl/hlsl_intrinsics.h  |  7 
 clang/lib/Sema/SemaHLSL.cpp   | 20 ++
 .../CodeGenHLSL/builtins/WaveReadLaneAt.hlsl  | 40 +++
 .../BuiltIns/WaveReadLaneAt-errors.hlsl   | 21 ++
 llvm/include/llvm/IR/IntrinsicsSPIRV.td   |  1 +
 .../Target/SPIRV/SPIRVInstructionSelector.cpp | 15 +++
 .../SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll   | 28 +
 10 files changed, 155 insertions(+)
 create mode 100644 clang/test/CodeGenHLSL/builtins/WaveReadLaneAt.hlsl
 create mode 100644 clang/test/SemaHLSL/BuiltIns/WaveReadLaneAt-errors.hlsl
 create mode 100644 llvm/test/CodeGen/SPIRV/hlsl-intrinsics/WaveReadLaneAt.ll

diff --git a/clang/include/clang/Basic/Builtins.td 
b/clang/include/clang/Basic/Builtins.td
index 8090119e512fbb..eec9acd4d27d7d 100644
--- a/clang/include/clang/Basic/Builtins.td
+++ b/clang/include/clang/Basic/Builtins.td
@@ -4703,6 +4703,12 @@ def HLSLWaveIsFirstLane : LangBuiltin<"HLSL_LANG"> {
   let Prototype = "bool()";
 }
 
+def HLSLWaveReadLaneAt : LangBuiltin<"HLSL_LANG"> {
+  let Spellings = ["__builtin_hlsl_wave_read_lane_at"];
+  let Attributes = [NoThrow, Const];
+  let Prototype = "void(...)";
+}
+
 def HLSLClamp : LangBuiltin<"HLSL_LANG"> {
   let Spellings = ["__builtin_hlsl_elementwise_clamp"];
   let Attributes = [NoThrow, Const];
diff --git a/clang/lib/CodeGen/CGBuiltin.cpp b/clang/lib/CodeGen/CGBuiltin.cpp
index da3eca73bfb575..dff56af9282e9d 100644
--- a/clang/lib/CodeGen/CGBuiltin.cpp
+++ b/clang/lib/CodeGen/CGBuiltin.cpp
@@ -18835,6 +18835,22 @@ case Builtin::BI__builtin_hlsl_elementwise_isinf: {
 Intrinsic::ID ID = CGM.getHLSLRuntime().getWaveIsFirstLaneIntrinsic();
 return EmitRuntimeCall(Intrinsic::getDeclaration(&CGM.getModule(), ID));
   }
+  case Builtin::BI__builtin_hlsl_wave_read_lane_at: {
+// Due to the use of variadic arguments we must explicitly retreive them 
and
+// create our function type.
+Value *OpExpr = EmitScalarExpr(E->getArg(0));
+Value *OpIndex = EmitScalarExpr(E->getArg(1));
+llvm::FunctionType *FT = llvm::FunctionType::get(
+OpExpr->getType(), ArrayRef{OpExpr->getType(), OpIndex->getType()},
+false);
+
+// Get overloaded name
+std::string name =
+Intrinsic::getName(CGM.getHLSLRuntime().getWaveReadLaneAtIntrinsic(),
+   ArrayRef{OpExpr->getType()}, &CGM.getModule());
+return EmitRuntimeCall(CGM.CreateRuntimeFunction(FT, name, {}, false, 
true),
+   ArrayRef{OpExpr, OpIndex}, 
"hlsl.wave.read.lane.at");
+  }
   case Builtin::BI__builtin_hlsl_elementwise_sign: {
 Value *Op0 = EmitScalarExpr(E->getArg(0));
 llvm::Type *Xty = Op0->getType();
diff --git a/clang/lib/CodeGen/CGHLSLRuntime.h 
b/clang/lib/CodeGen/CGHLSLRuntime.h
index a8aabca7348ffb..a639ce2d784f4a 100644
--- a/clang/lib/CodeGen/CGHLSLRuntime.h
+++ b/clang/lib/CodeGen/CGHLSLRuntime.h
@@ -87,6 +87,7 @@ class CGHLSLRuntime {
   GENERATE_HLSL_INTRINSIC_FUNCTION(SDot, sdot)
   GENERATE_HLSL_INTRINSIC_FUNCTION(UDot, udot)
   GENERATE_HLSL_INTRINSIC_FUNCTION(WaveIsFirstLane, wave_is_first_lane)
+  GENERATE_HLSL_INTRINSIC_FUNCTION(WaveReadLaneAt, wave_read_lane_at)
 
   
//===--===//
   // End of reserved area for HLSL intrinsic getters.
diff --git a/clang/lib/Headers/hlsl/hlsl_intrinsics.h 
b/clang/lib/Headers/hlsl/hlsl_intrinsics.h
index 810a16d75f0228..a7bdc353ae71bf 100644
--- a/clang/lib/Headers/hlsl/hlsl_intrinsics.h
+++ b/clang/lib/Headers/hlsl/hlsl_intrinsics.h
@@ -2015,6 +2015,13 @@ _HLSL_AVAILABILITY(shadermodel, 6.0)
 _HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_is_first_lane)
 __attribute__((convergent)) bool WaveIsFirstLane();
 
+// \brief Returns the value of the expression for the given lane index within
+// the specified wave.
+template 
+_HLSL_AVAILABILITY(shadermodel, 6.0)
+_HLSL_BUILTIN_ALIAS(__builtin_hlsl_wave_read_lane_at)
+__attribute__((convergent)) T WaveReadLaneAt(T, int32_t);
+
 
//===-

[clang] [llvm] [HLSL] Implement `WaveReadLaneAt` intrinsic (PR #111010)

2024-10-08 Thread Finn Plummer via cfe-commits


@@ -0,0 +1,26 @@
+// RUN: %clang_cc1 -finclude-default-header -triple 
dxil-pc-shadermodel6.6-library %s -fnative-half-type -emit-llvm-only 
-disable-llvm-passes -verify -verify-ignore-unexpected

inbelic wrote:

Good catch. There are no ignored diagnostics and it is not needed.

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


[clang] [clang] Allow `ConditionalOperator` fast-math flags to be overridden by `pragma float_control` (PR #105912)

2024-10-08 Thread Andy Kaylor via cfe-commits

andykaylor wrote:

> Yeah, the conditional operator doesn't do any floating-path math itself. If 
> the first operand is a floating-point expression, we should always be 
> modeling that with a float-to-boolean conversion, and the flags should go 
> there (if they're necessary — I didn't think comparisons were flag-sensitive).

Any instruction that returns a floating-point value can have fast-math flags 
attached to it, and because we need to check the fast-math flags on input 
operands, the select instruction generated by the conditional operator needs 
the flags set when fast-math is enabled. That's happening in the general case, 
but it isn't currently being modified correctly in the presence of pragmas.

https://godbolt.org/z/91zPx5ha4

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


[clang] [ItaniumCXXABI] Mark RTTI type name as global unnamed_addr (PR #111343)

2024-10-08 Thread via cfe-commits

luxufan wrote:

> https://itanium-cxx-abi.github.io/cxx-abi/abi.html#vague-rtti and 
> https://itanium-cxx-abi.github.io/cxx-abi/abi.html#typeid in the ABI require 
> the type name string to be globally unique, and some `std::type_info` 
> implementations rely on that. You might be able to do this for some specific 
> targets that choose a different ABI rule, but not in general.

Thanks for your reply!

Yes, you are right. I checked the llvm's libcxx code, Here 
https://github.com/llvm/llvm-project/blob/main/libcxx/include/typeinfo#L320, it 
compares the equality of two types by the address of type name string.

But, I have a question: now that it has ensured the uniqueness of typeinfo's 
address, why does the implementation still compare the type equality by the 
address of type name string?

> Specifically: we do perform address comparisons between these strings, so the 
> address is significant. And we can have identical string content but 
> different types:
> 
> * for types whose name involves anything with internal linkage
> * for types with hidden visibility
> * when loading a DSO using `RTLD_LOCAL`
> 
> so in a few cases allowing merging could be bad. Most of that only applies 
> during dynamic linking. Do we have a guarantee that `unnamed_addr` is dropped 
> before dynamic linking?

For symbols with internal linkage or hidden visibility, I don't think there 
would be problems if they were allowed to be merged. For example, considering 
there are 2 translation units 0.cpp and 1.cpp, and we defined internal `class A 
{}` in these 2 translation units, since they are all internal symbols, I think 
comparing `0.cpp::A` with `1.cpp::A` is undefined behavior. Because there at 
least one symbol was referenced outside of the current visibility scope.

For dynamic loading, if there are two same symbols in different DSOs, does this 
violates the C++ one-definition-rules?


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


[clang] [llvm] [clang][LLVM Demangler] Add an assertion that validates that all mang… (PR #111391)

2024-10-08 Thread Viktoriia Bakalova via cfe-commits


@@ -1967,6 +1967,10 @@ def fclang_abi_compat_EQ : Joined<["-"], 
"fclang-abi-compat=">, Group,
   MetaVarName<"">, Values<".,latest">,
   HelpText<"Attempt to match the ABI of Clang ">;
+def fno_demangling_failures: Flag<["-"], "fno-demangling-failures">, 
Group,

VitaNuo wrote:

Yeah this flag turns on an assertion that validates that all the manglings 
produced by clang can be demangled. In this sense it on & off (off by default). 
Let me know if I misunderstand something. 

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


[clang] [clang][RISCV] Extend intrinsic size check variable from 16 -> 32 bits. NFC (PR #111481)

2024-10-08 Thread Pengcheng Wang via cfe-commits

wangpc-pp wrote:

> Why don’t any of our lit tests that use every intrinsic catch it?

We don't see any error, is it because your downstream added some intrinsics?

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


[clang] [clang][RISCV] Extend intrinsic size check variable from 16 -> 32 bits. NFC (PR #111481)

2024-10-08 Thread Craig Topper via cfe-commits

topperc wrote:

Why don’t any of our lit tests that use every intrinsic catch it?

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


[clang] [llvm] [clang][LLVM Demangler] Add an assertion that validates that all mang… (PR #111391)

2024-10-08 Thread Viktoriia Bakalova via cfe-commits


@@ -462,6 +462,9 @@ ENUM_CODEGENOPT(ZeroCallUsedRegs, 
llvm::ZeroCallUsedRegs::ZeroCallUsedRegsKind,
 /// non-deleting destructors. (No effect on Microsoft ABI.)
 CODEGENOPT(CtorDtorReturnThis, 1, 0)
 
+/// Whether to validate if a produced mangled name can be demangled with LLVM 
demangler.
+CODEGENOPT(NoDemanglingFailures, 1, 0)

VitaNuo wrote:

The macro signature is `CODEGENOPT(Name, Bits, Default)`, so I assume you're 
referring to the `Default` as being inverted (the bit count is 1, since this is 
a flag).

IIUC `0` means that the flag is off (= don't apply the assertion), `1` means 
the flag is on (= apply the assertion and validate that mangled names can be 
demangled). We don't want to set the flag to on by default, so `0` seems right.

Could you explain why you believe this inverted? I'm probably missing something.

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


[clang] [llvm] [clang][LLVM Demangler] Add an assertion that validates that all mang… (PR #111391)

2024-10-08 Thread Viktoriia Bakalova via cfe-commits

https://github.com/VitaNuo edited 
https://github.com/llvm/llvm-project/pull/111391
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang][RISCV] Extend intrinsic size check variable from 16 -> 32 bits. NFC (PR #111481)

2024-10-08 Thread Craig Topper via cfe-commits


@@ -399,7 +399,7 @@ void RISCVIntrinsicManagerImpl::InitRVVIntrinsic(
  Record.HasFRMRoundModeOp);
 
   // Put into IntrinsicList.
-  uint16_t Index = IntrinsicList.size();
+  uint32_t Index = IntrinsicList.size();

topperc wrote:

What is the type of Intrinsics on this line further down

```
Intrinsics.insert({Name, Index});
```

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


[clang] [clang][RISCV] Extend intrinsic size check variable from 16 -> 32 bits. NFC (PR #111481)

2024-10-08 Thread Craig Topper via cfe-commits

https://github.com/topperc edited 
https://github.com/llvm/llvm-project/pull/111481
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] check deduction consistency when partial ordering function templates (PR #100692)

2024-10-08 Thread Yi Kong via cfe-commits

kongy wrote:

There is a case that becomes invalid with this patch, is it expected behaviour?

```
template  struct Traits {
  using Type = Traits;
};
template 
void bar(typename Traits::Type... args) {
  FillVRegs(args...);
}
template  void FillVRegs(typename Traits::Type...);
template 
void FillVRegs(typename Traits::Type,
   typename Traits::Type);
void foo() { bar<'A', 'A'>; }
```

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


[clang] [clang][Sema] Bad register variable type error should point to the type (PR #110239)

2024-10-08 Thread via cfe-commits

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

Looks like CI is still mad at you for some reason so that still needs to be 
looked into, but other than that this lgtm.

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


[clang] [clang][RISCV] Extend intrinsic size check variable from 16 -> 32 bits. NFC (PR #111481)

2024-10-08 Thread Craig Topper via cfe-commits

topperc wrote:

Does the number intrinsics vary with the number of extensions enabled? Maybe we 
don't have a test with all extensions?

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


[clang] Effect analysis: correctly detect `(x ? a : b)` as nonblocking when a and b are (PR #111224)

2024-10-08 Thread via cfe-commits

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

LGTM

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


[clang] Effect analysis: correctly detect `(x ? a : b)` as nonblocking when a and b are (PR #111224)

2024-10-08 Thread via cfe-commits

https://github.com/Sirraide closed 
https://github.com/llvm/llvm-project/pull/111224
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] 4d218ca - [Clang] [Sema] Effects: Correctly detect `(x ? a : b)` as nonblocking when a and b are (#111224)

2024-10-08 Thread via cfe-commits

Author: Doug Wyatt
Date: 2024-10-08T10:20:05+02:00
New Revision: 4d218caa7716743061e8d34d61b2181c94b16440

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

LOG: [Clang] [Sema] Effects: Correctly detect `(x ? a : b)` as nonblocking when 
a and b are (#111224)

Correctly detect `(x ? a : b)` as nonblocking when `a` and `b` are. Use 
`FunctionEffectsRef::get` to get to the actual effect set instead of trying 
to retrieve it manually via the `FunctionProtoType` as we may have to 
look through function pointers etc. in some cases.

-

Co-authored-by: Doug Wyatt 

Added: 


Modified: 
clang/lib/Sema/SemaFunctionEffects.cpp
clang/test/Sema/attr-nonblocking-constraints.cpp

Removed: 




diff  --git a/clang/lib/Sema/SemaFunctionEffects.cpp 
b/clang/lib/Sema/SemaFunctionEffects.cpp
index 0fb18d207a50ba..0ac5de29f66aa7 100644
--- a/clang/lib/Sema/SemaFunctionEffects.cpp
+++ b/clang/lib/Sema/SemaFunctionEffects.cpp
@@ -1048,15 +1048,14 @@ class Analyzer {
 }
 
 void checkIndirectCall(CallExpr *Call, QualType CalleeType) {
-  auto *FPT =
-  CalleeType->getAs(); // Null if FunctionType.
   FunctionEffectKindSet CalleeEffects;
-  if (FPT)
-CalleeEffects.insert(FPT->getFunctionEffects());
+  if (FunctionEffectsRef Effects = FunctionEffectsRef::get(CalleeType);
+  !Effects.empty())
+CalleeEffects.insert(Effects);
 
   auto Check1Effect = [&](FunctionEffect Effect, bool Inferring) {
-if (FPT == nullptr || Effect.shouldDiagnoseFunctionCall(
-  /*direct=*/false, CalleeEffects))
+if (Effect.shouldDiagnoseFunctionCall(
+/*direct=*/false, CalleeEffects))
   addViolation(Inferring, Effect, ViolationID::CallsExprWithoutEffect,
Call->getBeginLoc());
   };

diff  --git a/clang/test/Sema/attr-nonblocking-constraints.cpp 
b/clang/test/Sema/attr-nonblocking-constraints.cpp
index c694860069c960..f23093d4dc8a96 100644
--- a/clang/test/Sema/attr-nonblocking-constraints.cpp
+++ b/clang/test/Sema/attr-nonblocking-constraints.cpp
@@ -156,6 +156,17 @@ void nb10(
static_cast(fp1)(); // expected-warning {{function with 
'nonblocking' attribute must not call non-'nonblocking' expression}}
 }
 
+// Expression involving indirection
+int nb10a() [[clang::nonblocking]];
+int nb10b() [[clang::nonblocking]];
+int blocking();
+
+int nb10c(bool x) [[clang::nonblocking]]
+{
+   int y = (x ? nb10a : blocking)(); // expected-warning {{attribute 
'nonblocking' should not be added via type conversion}}
+   return (x ? nb10a : nb10b)(); // No diagnostic.
+}
+
 // Interactions with nonblocking(false)
 void nb11_no_inference_1() [[clang::nonblocking(false)]] // expected-note 
{{function does not permit inference of 'nonblocking'}}
 {



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [llvm] [clang][LLVM Demangler] Add an assertion that validates that all mang… (PR #111391)

2024-10-08 Thread Viktoriia Bakalova via cfe-commits

VitaNuo wrote:

> Since this is being done as an assert, this is something that really only 
> applies during debug mode. I dont think this compiler flag makes sense 
> because of it.

The reason I am adding a flag on top of an assert is that there are 
unfortunately still many mangled names produced by `clang` that cannot be 
demangled. E.g., many of the existing codegen lit tests 
(`clang/test/CodeGenCXX/*`) fail in assertion-enabled builds without the flag. 
This is potentially disruptive to development workflows. The flag can be 
removed once the LLVM demangler can handle all the mangled names `clang` 
produces.

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


[clang] Effect analysis: correctly detect `(x ? a : b)` as nonblocking when a and b are (PR #111224)

2024-10-08 Thread via cfe-commits

Sirraide wrote:

@dougsonos Maybe you should ask for commit access since you’ll likely be 
contributing more patches to this in the future as I understand it?

CC @AaronBallman Does that still work like it used to or did your maintainers 
rfc change something about that too?

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


[clang] Effect analysis: correctly detect `(x ? a : b)` as nonblocking when a and b are (PR #111224)

2024-10-08 Thread via cfe-commits

Sirraide wrote:

Oh, also, are there any other places where we should maybe be using 
`FunctionEffectsRef::get()`?

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


[clang] f658c1b - Recommit "[RISCV][FMV] Support target_version" (#111096)" (#111333)

2024-10-08 Thread via cfe-commits

Author: Piyou Chen
Date: 2024-10-08T16:26:55+08:00
New Revision: f658c1bf4a9d74518ff55a37184b76ec5dec9a8b

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

LOG: Recommit "[RISCV][FMV] Support target_version" (#111096)" (#111333)

Fix the buildbot failure caused by heap use-after-free error.

Origin message:

This patch enable `target_version` attribute for RISC-V target.

The proposal of `target_version` syntax can be found at the
https://github.com/riscv-non-isa/riscv-c-api-doc/pull/48 (which has
landed), as modified by the proposed
https://github.com/riscv-non-isa/riscv-c-api-doc/pull/85 (which adds the
priority syntax).

`target_version` attribute will trigger the function multi-versioning
feature and act like `target_clones` attribute. See
https://github.com/llvm/llvm-project/pull/85786 for the implementation
of `target_clones`.

Added: 
clang/test/CodeGen/attr-target-version-riscv-invalid.c
clang/test/CodeGen/attr-target-version-riscv.c
clang/test/CodeGenCXX/attr-target-version-riscv.cpp
clang/test/SemaCXX/attr-target-version-riscv.cpp

Modified: 
clang/lib/AST/ASTContext.cpp
clang/lib/CodeGen/CodeGenModule.cpp
clang/lib/Sema/SemaDecl.cpp
clang/lib/Sema/SemaDeclAttr.cpp

Removed: 




diff  --git a/clang/lib/AST/ASTContext.cpp b/clang/lib/AST/ASTContext.cpp
index a81429ad6a2380..034fbbe0bc7829 100644
--- a/clang/lib/AST/ASTContext.cpp
+++ b/clang/lib/AST/ASTContext.cpp
@@ -14325,9 +14325,17 @@ void 
ASTContext::getFunctionFeatureMap(llvm::StringMap &FeatureMap,
   Target->initFeatureMap(FeatureMap, getDiagnostics(), TargetCPU, 
Features);
 }
   } else if (const auto *TV = FD->getAttr()) {
-llvm::SmallVector Feats;
-TV->getFeatures(Feats);
-std::vector Features = getFMVBackendFeaturesFor(Feats);
+std::vector Features;
+if (Target->getTriple().isRISCV()) {
+  ParsedTargetAttr ParsedAttr = Target->parseTargetAttr(TV->getName());
+  Features.insert(Features.begin(), ParsedAttr.Features.begin(),
+  ParsedAttr.Features.end());
+} else {
+  assert(Target->getTriple().isAArch64());
+  llvm::SmallVector Feats;
+  TV->getFeatures(Feats);
+  Features = getFMVBackendFeaturesFor(Feats);
+}
 Features.insert(Features.begin(),
 Target->getTargetOpts().FeaturesAsWritten.begin(),
 Target->getTargetOpts().FeaturesAsWritten.end());

diff  --git a/clang/lib/CodeGen/CodeGenModule.cpp 
b/clang/lib/CodeGen/CodeGenModule.cpp
index 25c1c496a4f27f..5ba098144a74e7 100644
--- a/clang/lib/CodeGen/CodeGenModule.cpp
+++ b/clang/lib/CodeGen/CodeGenModule.cpp
@@ -4287,8 +4287,13 @@ void CodeGenModule::emitMultiVersionFunctions() {
   } else if (const auto *TVA = CurFD->getAttr()) {
 if (TVA->isDefaultVersion() && IsDefined)
   ShouldEmitResolver = true;
-TVA->getFeatures(Feats);
 llvm::Function *Func = createFunction(CurFD);
+if (getTarget().getTriple().isRISCV()) {
+  Feats.push_back(TVA->getName());
+} else {
+  assert(getTarget().getTriple().isAArch64());
+  TVA->getFeatures(Feats);
+}
 Options.emplace_back(Func, /*Architecture*/ "", Feats);
   } else if (const auto *TC = CurFD->getAttr()) {
 if (IsDefined)

diff  --git a/clang/lib/Sema/SemaDecl.cpp b/clang/lib/Sema/SemaDecl.cpp
index 2bf610746bc317..5c4e0562152c5b 100644
--- a/clang/lib/Sema/SemaDecl.cpp
+++ b/clang/lib/Sema/SemaDecl.cpp
@@ -10329,7 +10329,8 @@ Sema::ActOnFunctionDeclarator(Scope *S, Declarator &D, 
DeclContext *DC,
   // Handle attributes.
   ProcessDeclAttributes(S, NewFD, D);
   const auto *NewTVA = NewFD->getAttr();
-  if (NewTVA && !NewTVA->isDefaultVersion() &&
+  if (Context.getTargetInfo().getTriple().isAArch64() && NewTVA &&
+  !NewTVA->isDefaultVersion() &&
   !Context.getTargetInfo().hasFeature("fmv")) {
 // Don't add to scope fmv functions declarations if fmv disabled
 AddToScope = false;
@@ -11038,7 +11039,16 @@ static bool CheckMultiVersionValue(Sema &S, const 
FunctionDecl *FD) {
 
   if (TVA) {
 llvm::SmallVector Feats;
-TVA->getFeatures(Feats);
+ParsedTargetAttr ParseInfo;
+if (S.getASTContext().getTargetInfo().getTriple().isRISCV()) {
+  ParseInfo =
+  S.getASTContext().getTargetInfo().parseTargetAttr(TVA->getName());
+  for (auto &Feat : ParseInfo.Features)
+Feats.push_back(StringRef{Feat}.substr(1));
+} else {
+  assert(S.getASTContext().getTargetInfo().getTriple().isAArch64());
+  TVA->getFeatures(Feats);
+}
 for (const auto &Feat : Feats) {
   if (!TargetInfo.validateCpuSupports(Feat)) {
 S.Diag(FD

[clang] Recommit "[RISCV][FMV] Support target_version" (#111096)" (PR #111333)

2024-10-08 Thread Piyou Chen via cfe-commits

https://github.com/BeMg closed https://github.com/llvm/llvm-project/pull/111333
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [clang] Introduce [[clang::lifetime_capture_by(X)]] (PR #111499)

2024-10-08 Thread Utkarsh Saxena via cfe-commits

https://github.com/usx95 created 
https://github.com/llvm/llvm-project/pull/111499

This implements the RFC 
https://discourse.llvm.org/t/rfc-introduce-clang-lifetime-capture-by-x/81371

>From b1368f676ac5f55741df021c2697d3b46fd2c92d Mon Sep 17 00:00:00 2001
From: Utkarsh Saxena 
Date: Tue, 8 Oct 2024 08:19:56 +
Subject: [PATCH] start working on lifetime capture

---
 clang/include/clang/Basic/Attr.td | 35 
 .../clang/Basic/DiagnosticSemaKinds.td| 15 
 clang/include/clang/Sema/Sema.h   |  5 ++
 clang/lib/AST/TypePrinter.cpp |  1 +
 clang/lib/Sema/CheckExprLifetime.cpp  | 26 +-
 clang/lib/Sema/CheckExprLifetime.h|  3 +
 clang/lib/Sema/SemaChecking.cpp   | 26 ++
 clang/lib/Sema/SemaDecl.cpp   |  1 +
 clang/lib/Sema/SemaDeclAttr.cpp   | 79 ++
 clang/lib/Sema/SemaType.cpp   | 13 +++
 clang/test/SemaCXX/attr-lifetimebound.cpp | 80 +++
 11 files changed, 283 insertions(+), 1 deletion(-)

diff --git a/clang/include/clang/Basic/Attr.td 
b/clang/include/clang/Basic/Attr.td
index 35b9716e13ff21..8307d8d19c7fec 100644
--- a/clang/include/clang/Basic/Attr.td
+++ b/clang/include/clang/Basic/Attr.td
@@ -1869,6 +1869,41 @@ def LifetimeBound : DeclOrTypeAttr {
   let SimpleHandler = 1;
 }
 
+def LifetimeCaptureBy : DeclOrTypeAttr {
+  let Spellings = [Clang<"lifetime_capture_by", 0>];
+  let Subjects = SubjectList<[ParmVar, ImplicitObjectParameter], ErrorDiag>;
+  let Args = [VariadicParamOrParamIdxArgument<"Params">];
+  let Documentation = [LifetimeBoundDocs];
+  let LangOpts = [CPlusPlus];
+
+  // let SimpleHandler = 1;
+  // let LateParsed = LateAttrParseStandard;
+  // let HasCustomParsing = 1;
+  // let ParseArgumentsAsUnevaluated = 1;
+
+  let AdditionalMembers = [{
+private:
+  SmallVector ArgIdents;
+  SmallVector ArgLocs;
+
+public:
+  void setArgs(SmallVector Idents,
+   SmallVector Locs) { 
+assert(Idents.size() == Locs.size());
+assert(Idents.size() == params_Size);
+ArgIdents = std::move(Idents);
+ArgLocs = std::move(Locs);
+  }
+  
+  const SmallVector& getArgIdents() const { return 
ArgIdents; }
+  const SmallVector& getArgLocs() const { return ArgLocs; }
+  void setParamIdx(size_t Idx, int Val) { 
+assert(Idx < params_Size);
+params_[Idx] = Val;
+  }
+}];
+}
+
 def TrivialABI : InheritableAttr {
   // This attribute does not have a C [[]] spelling because it requires the
   // CPlusPlus language option.
diff --git a/clang/include/clang/Basic/DiagnosticSemaKinds.td 
b/clang/include/clang/Basic/DiagnosticSemaKinds.td
index e8b64f3c5a0187..94b2b9252ff834 100644
--- a/clang/include/clang/Basic/DiagnosticSemaKinds.td
+++ b/clang/include/clang/Basic/DiagnosticSemaKinds.td
@@ -3382,6 +3382,17 @@ def err_callback_callee_is_variadic : Error<
   "'callback' attribute callee may not be variadic">;
 def err_callback_implicit_this_not_available : Error<
   "'callback' argument at position %0 references unavailable implicit 'this'">;
+
+def err_capture_by_attribute_multiple : Error<
+  "multiple 'lifetime_capture' attributes specified">;
+def err_capture_by_attribute_no_entity : Error<
+  "'lifetime_capture_by' attribute specifies no capturing entity">;
+def err_capture_by_implicit_this_not_available : Error<
+  "'lifetime_capture_by' argument references unavailable implicit 'this'">;
+def err_capture_by_attribute_argument_unknown : Error<
+  "'lifetime_capture_by' attribute argument %0 is not a known function 
parameter"
+  ". Must be a function parameter of one of 'this', 'global' or 'unknown'">;
+
 def err_init_method_bad_return_type : Error<
   "init methods must return an object pointer type, not %0">;
 def err_attribute_invalid_size : Error<
@@ -10185,6 +10196,10 @@ def warn_dangling_pointer_assignment : Warning<
"object backing the pointer %0 "
"will be destroyed at the end of the full-expression">,
InGroup;
+def warn_dangling_reference_captured : Warning<
+   "object captured by the '%0' "
+   "will be destroyed at the end of the full-expression">,
+   InGroup;
 
 // For non-floating point, expressions of the form x == x or x != x
 // should result in a warning, since these always evaluate to a constant.
diff --git a/clang/include/clang/Sema/Sema.h b/clang/include/clang/Sema/Sema.h
index 0809ac1b144ef6..26b648868d7eb4 100644
--- a/clang/include/clang/Sema/Sema.h
+++ b/clang/include/clang/Sema/Sema.h
@@ -1830,6 +1830,8 @@ class Sema final : public SemaBase {
   /// Add [[gsl::Pointer]] attributes for std:: types.
   void inferGslPointerAttribute(TypedefNameDecl *TD);
 
+  void lazyProcessLifetimeCaptureByParams(FunctionDecl *FD);
+
   /// Add _Nullable attributes for std:: types.
   void inferNullableClassAttribute(CXXRecordDecl *CRD);
 
@@ -2384,6 +2386,9 @@ class Sema final : public SemaBase {
   bool BuiltinVectorMath(CallExpr *TheCall, QualType &Res);
   bool BuiltinVectorToScala

[clang] [Clang] Instantiate the correct lambda call operator (PR #110446)

2024-10-08 Thread via cfe-commits

https://github.com/Sirraide updated 
https://github.com/llvm/llvm-project/pull/110446

>From a61f3e94d0636f4294f3be440d79b83889771800 Mon Sep 17 00:00:00 2001
From: Sirraide 
Date: Mon, 30 Sep 2024 02:58:31 +0200
Subject: [PATCH 1/3] [Clang] Instantiate the correct lambda call operator

---
 clang/docs/ReleaseNotes.rst  |  1 +
 clang/lib/AST/DeclCXX.cpp| 27 ++--
 clang/test/Modules/gh110401.cppm | 44 
 3 files changed, 70 insertions(+), 2 deletions(-)
 create mode 100644 clang/test/Modules/gh110401.cppm

diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index 14907e7db18de3..17a0c45d98c5c8 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -426,6 +426,7 @@ Bug Fixes to C++ Support
 - Fixed an assertion failure in debug mode, and potential crashes in release 
mode, when
   diagnosing a failed cast caused indirectly by a failed implicit conversion 
to the type of the constructor parameter.
 - Fixed an assertion failure by adjusting integral to boolean vector 
conversions (#GH108326)
+- Clang now instantiates the correct lambda call operator when a lambda's 
class type is merged across modules. (#GH110401)
 
 Bug Fixes to AST Handling
 ^
diff --git a/clang/lib/AST/DeclCXX.cpp b/clang/lib/AST/DeclCXX.cpp
index 01143391edab40..af9c644337c84d 100644
--- a/clang/lib/AST/DeclCXX.cpp
+++ b/clang/lib/AST/DeclCXX.cpp
@@ -1631,9 +1631,32 @@ static bool allLookupResultsAreTheSame(const 
DeclContext::lookup_result &R) {
 static NamedDecl* getLambdaCallOperatorHelper(const CXXRecordDecl &RD) {
   if (!RD.isLambda()) return nullptr;
   DeclarationName Name =
-RD.getASTContext().DeclarationNames.getCXXOperatorName(OO_Call);
-  DeclContext::lookup_result Calls = RD.lookup(Name);
+  RD.getASTContext().DeclarationNames.getCXXOperatorName(OO_Call);
+
+  // If we have multiple call operators, we might be in a situation
+  // where we merged this lambda with one from another module; in that
+  // case, return our method (instead of that of the other lambda).
+  //
+  // This avoids situations where, given two modules A and B, if we
+  // try to instantiate A's call operator in a function in B, anything
+  // in the call operator that relies on local decls in the surrounding
+  // function will crash because it tries to find A's decls, but we only
+  // instantiated B's:
+  //
+  //   template 
+  //   void f() {
+  // using T = int;  // We only instantiate B's version of this.
+  // auto L = [](T) { }; // But A's call operator wants A's here.
+  //   }
+  //
+  // To mitigate this, search our own decls first.
+  // FIXME: This feels like a hack; is there a better way of doing this?
+  for (CXXMethodDecl *M : RD.methods())
+if (M->getDeclName() == Name)
+  return M;
 
+  // Otherwise, do a full lookup to find external decls too.
+  DeclContext::lookup_result Calls = RD.lookup(Name);
   assert(!Calls.empty() && "Missing lambda call operator!");
   assert(allLookupResultsAreTheSame(Calls) &&
  "More than one lambda call operator!");
diff --git a/clang/test/Modules/gh110401.cppm b/clang/test/Modules/gh110401.cppm
new file mode 100644
index 00..6b335eb5ba9d55
--- /dev/null
+++ b/clang/test/Modules/gh110401.cppm
@@ -0,0 +1,44 @@
+// RUN: rm -rf %t
+// RUN: mkdir %t
+// RUN: split-file %s %t
+//
+// RUN: %clang_cc1 -std=c++20 -triple x86_64-unknown-linux 
-emit-module-interface %t/a.cppm -o %t/A.pcm
+// RUN: %clang_cc1 -std=c++20 -triple x86_64-unknown-linux 
-emit-module-interface -fprebuilt-module-path=%t %t/b.cppm -o %t/B.pcm
+
+// Just check that this doesn't crash.
+
+//--- a.cppm
+module;
+
+template 
+void __do_visit(_Visitor &&__visitor) {
+  using _V0 = int;
+  [](_V0 __v) -> _V0 { return __v; } (1);
+}
+
+export module A;
+
+void g() {
+  struct Visitor { };
+  __do_visit(Visitor());
+}
+
+//--- b.cppm
+module;
+
+template 
+void __do_visit(_Visitor &&__visitor) {
+  using _V0 = int;
+
+  // Check that we instantiate this lambda's call operator in 'f' below
+  // instead of the one in 'a.cppm' here; otherwise, we won't find a
+  // corresponding instantiation of the using declaration above.
+  [](_V0 __v) -> _V0 { return __v; } (1);
+}
+
+export module B;
+import A;
+
+void f() {
+  __do_visit(1);
+}

>From d3b5acc0a43bf227d57b3d7f1c68acedb89e3123 Mon Sep 17 00:00:00 2001
From: Sirraide 
Date: Mon, 30 Sep 2024 17:34:43 +0200
Subject: [PATCH 2/3] Walk redecl chain to find the right operator

---
 clang/lib/AST/DeclCXX.cpp | 27 +++
 1 file changed, 15 insertions(+), 12 deletions(-)

diff --git a/clang/lib/AST/DeclCXX.cpp b/clang/lib/AST/DeclCXX.cpp
index af9c644337c84d..da7a8ac0e5fe0f 100644
--- a/clang/lib/AST/DeclCXX.cpp
+++ b/clang/lib/AST/DeclCXX.cpp
@@ -1633,6 +1633,11 @@ static NamedDecl* getLambdaCallOperatorHelper(const 
CXXRecordDecl &RD) {
   DeclarationName Name =
   RD.getASTContext().DeclarationNames.getCXXOpe

[clang] [llvm] [ARM] Fix musttail calls (PR #109943)

2024-10-08 Thread Oliver Stannard via cfe-commits

https://github.com/ostannard updated 
https://github.com/llvm/llvm-project/pull/109943

>From 9b2646806978429395232ed596429ef281bcb26b Mon Sep 17 00:00:00 2001
From: Oliver Stannard 
Date: Thu, 9 May 2024 12:58:41 +0100
Subject: [PATCH 01/10] [ARM] Re-generate a test

---
 llvm/test/CodeGen/ARM/fp-arg-shuffle.ll | 24 
 1 file changed, 24 insertions(+)

diff --git a/llvm/test/CodeGen/ARM/fp-arg-shuffle.ll 
b/llvm/test/CodeGen/ARM/fp-arg-shuffle.ll
index 4996cc8ecbf022..36f5a4b30af409 100644
--- a/llvm/test/CodeGen/ARM/fp-arg-shuffle.ll
+++ b/llvm/test/CodeGen/ARM/fp-arg-shuffle.ll
@@ -1,8 +1,32 @@
+; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py 
UTC_ARGS: --version 4
 ; RUN: llc -mtriple=arm-eabi -mattr=+neon -float-abi=soft %s -o - | FileCheck 
%s
 
 ; CHECK: function1
 ; CHECK-NOT: vmov
 define double @function1(double %a, double %b, double %c, double %d, double 
%e, double %f) nounwind noinline ssp {
+; CHECK-LABEL: function1:
+; CHECK:   @ %bb.0: @ %entry
+; CHECK-NEXT:.save {r4, r5, r11, lr}
+; CHECK-NEXT:push {r4, r5, r11, lr}
+; CHECK-NEXT:.pad #32
+; CHECK-NEXT:sub sp, sp, #32
+; CHECK-NEXT:add lr, sp, #64
+; CHECK-NEXT:vldr d16, [sp, #56]
+; CHECK-NEXT:str r2, [sp, #16]
+; CHECK-NEXT:ldm lr, {r4, r5, r12, lr}
+; CHECK-NEXT:str r3, [sp, #20]
+; CHECK-NEXT:mov r3, r5
+; CHECK-NEXT:str r0, [sp, #24]
+; CHECK-NEXT:mov r0, r12
+; CHECK-NEXT:str r1, [sp, #28]
+; CHECK-NEXT:mov r1, lr
+; CHECK-NEXT:mov r2, r4
+; CHECK-NEXT:vldr d17, [sp, #48]
+; CHECK-NEXT:vstmia sp, {d16, d17}
+; CHECK-NEXT:bl function2
+; CHECK-NEXT:add sp, sp, #32
+; CHECK-NEXT:pop {r4, r5, r11, lr}
+; CHECK-NEXT:mov pc, lr
 entry:
   %call = tail call double @function2(double %f, double %e, double %d, double 
%c, double %b, double %a) nounwind
   ret double %call

>From 07a5a3dea3c295db81fac6ef50a1b2371f9894cf Mon Sep 17 00:00:00 2001
From: Oliver Stannard 
Date: Tue, 24 Sep 2024 10:46:47 +0100
Subject: [PATCH 02/10] [ARM] Fix comment typo

---
 llvm/lib/Target/ARM/ARMISelLowering.cpp | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/llvm/lib/Target/ARM/ARMISelLowering.cpp 
b/llvm/lib/Target/ARM/ARMISelLowering.cpp
index 1733424a8b669f..673cd57b45a96b 100644
--- a/llvm/lib/Target/ARM/ARMISelLowering.cpp
+++ b/llvm/lib/Target/ARM/ARMISelLowering.cpp
@@ -2408,8 +2408,8 @@ 
ARMTargetLowering::LowerCall(TargetLowering::CallLoweringInfo &CLI,
 isTailCall = false;
 
   // For both the non-secure calls and the returns from a CMSE entry function,
-  // the function needs to do some extra work afte r the call, or before the
-  // return, respectively, thus it cannot end with atail call
+  // the function needs to do some extra work after the call, or before the
+  // return, respectively, thus it cannot end with a tail call
   if (isCmseNSCall || AFI->isCmseNSEntryFunction())
 isTailCall = false;
 

>From 7773f66a711879ec884b92f56cc45e89ac44095b Mon Sep 17 00:00:00 2001
From: Oliver Stannard 
Date: Thu, 9 May 2024 13:00:46 +0100
Subject: [PATCH 03/10] [ARM] Add debug trace for tail-call optimisation

There are lots of reasons a call might not be eligible for tail-call
optimisation, this adds debug trace to help understand the compiler's
decisions here.
---
 llvm/lib/Target/ARM/ARMISelLowering.cpp | 64 +++--
 1 file changed, 49 insertions(+), 15 deletions(-)

diff --git a/llvm/lib/Target/ARM/ARMISelLowering.cpp 
b/llvm/lib/Target/ARM/ARMISelLowering.cpp
index 673cd57b45a96b..078a12246c2e08 100644
--- a/llvm/lib/Target/ARM/ARMISelLowering.cpp
+++ b/llvm/lib/Target/ARM/ARMISelLowering.cpp
@@ -3047,8 +3047,10 @@ bool 
ARMTargetLowering::IsEligibleForTailCallOptimization(
 for (const CCValAssign &AL : ArgLocs)
   if (AL.isRegLoc())
 AddressRegisters.erase(AL.getLocReg());
-if (AddressRegisters.empty())
+if (AddressRegisters.empty()) {
+  LLVM_DEBUG(dbgs() << "false (no reg to hold function pointer)\n");
   return false;
+}
   }
 
   // Look for obvious safe cases to perform tail call optimization that do not
@@ -3057,18 +3059,26 @@ bool 
ARMTargetLowering::IsEligibleForTailCallOptimization(
   // Exception-handling functions need a special set of instructions to 
indicate
   // a return to the hardware. Tail-calling another function would probably
   // break this.
-  if (CallerF.hasFnAttribute("interrupt"))
+  if (CallerF.hasFnAttribute("interrupt")) {
+LLVM_DEBUG(dbgs() << "false (interrupt attribute)\n");
 return false;
+  }
 
-  if (canGuaranteeTCO(CalleeCC, 
getTargetMachine().Options.GuaranteedTailCallOpt))
+  if (canGuaranteeTCO(CalleeCC,
+  getTargetMachine().Options.GuaranteedTailCallOpt)) {
+LLVM_DEBUG(dbgs() << (CalleeCC == CallerCC ? "true" : "false")
+  << " (guaranteed tail-call CC)\n");
 return CalleeCC == CallerCC;
+  }
 
   // Also avoid sibcall optim

[clang] [llvm] [ARM] Fix musttail calls (PR #109943)

2024-10-08 Thread Oliver Stannard via cfe-commits


@@ -0,0 +1,345 @@
+; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py 
UTC_ARGS: --version 5
+; RUN: llc -mtriple=armv7a-none-eabi %s -o - | FileCheck %s
+
+declare i32 @many_args_callee(i32 %0, i32 %1, i32 %2, i32 %3, i32 %4, i32 %5)
+
+define i32 @many_args_tail(i32 %0, i32 %1, i32 %2, i32 %3, i32  %4, i32  %5) {
+; CHECK-LABEL: many_args_tail:
+; CHECK:   @ %bb.0:
+; CHECK-NEXT:mov r0, #5
+; CHECK-NEXT:mov r1, #2
+; CHECK-NEXT:str r0, [sp]
+; CHECK-NEXT:mov r0, #6
+; CHECK-NEXT:str r0, [sp, #4]
+; CHECK-NEXT:mov r0, #1
+; CHECK-NEXT:mov r2, #3
+; CHECK-NEXT:mov r3, #4
+; CHECK-NEXT:b many_args_callee
+  %ret = tail call i32 @many_args_callee(i32 1, i32 2, i32 3, i32 4, i32 5, 
i32 6)
+  ret i32 %ret
+}
+
+define i32 @many_args_musttail(i32 %0, i32 %1, i32 %2, i32 %3, i32  %4, i32  
%5) {
+; CHECK-LABEL: many_args_musttail:
+; CHECK:   @ %bb.0:
+; CHECK-NEXT:mov r0, #5
+; CHECK-NEXT:mov r1, #2
+; CHECK-NEXT:str r0, [sp]
+; CHECK-NEXT:mov r0, #6
+; CHECK-NEXT:str r0, [sp, #4]
+; CHECK-NEXT:mov r0, #1
+; CHECK-NEXT:mov r2, #3
+; CHECK-NEXT:mov r3, #4
+; CHECK-NEXT:b many_args_callee
+  %ret = musttail call i32 @many_args_callee(i32 1, i32 2, i32 3, i32 4, i32 
5, i32 6)
+  ret i32 %ret
+}
+
+; This function has more arguments than it's tail-callee. This isn't valid for
+; the musttail attribute, but can still be tail-called as a non-guaranteed
+; optimisation, because the outgoing arguments to @many_args_callee fit in the
+; stack space allocated by the caller of @more_args_tail.
+define i32 @more_args_tail(i32 %0, i32 %1, i32 %2, i32 %3, i32  %4, i32 %5, 
i32 %6) {
+; CHECK-LABEL: more_args_tail:
+; CHECK:   @ %bb.0:
+; CHECK-NEXT:mov r0, #5
+; CHECK-NEXT:mov r1, #2
+; CHECK-NEXT:str r0, [sp]
+; CHECK-NEXT:mov r0, #6
+; CHECK-NEXT:str r0, [sp, #4]
+; CHECK-NEXT:mov r0, #1
+; CHECK-NEXT:mov r2, #3
+; CHECK-NEXT:mov r3, #4
+; CHECK-NEXT:b many_args_callee
+  %ret = tail call i32 @many_args_callee(i32 1, i32 2, i32 3, i32 4, i32 5, 
i32 6)
+  ret i32 %ret
+}
+
+; Again, this isn't valid for musttail, but can be tail-called in practice
+; because the stack size if the same.
+define i32 @different_args_tail(i64 %0, i64 %1, i64 %2) {
+; CHECK-LABEL: different_args_tail:
+; CHECK:   @ %bb.0:
+; CHECK-NEXT:mov r0, #5
+; CHECK-NEXT:mov r1, #2
+; CHECK-NEXT:str r0, [sp]
+; CHECK-NEXT:mov r0, #6
+; CHECK-NEXT:str r0, [sp, #4]
+; CHECK-NEXT:mov r0, #1
+; CHECK-NEXT:mov r2, #3
+; CHECK-NEXT:mov r3, #4
+; CHECK-NEXT:b many_args_callee
+  %ret = tail call i32 @many_args_callee(i32 1, i32 2, i32 3, i32 4, i32 5, 
i32 6)
+  ret i32 %ret
+}
+
+; Here, the caller requires less stack space for it's arguments than the
+; callee, so it would not ba valid to do a tail-call.
+define i32 @fewer_args_tail(i32 %0, i32 %1, i32 %2, i32 %3, i32  %4) {
+; CHECK-LABEL: fewer_args_tail:
+; CHECK:   @ %bb.0:
+; CHECK-NEXT:.save {r11, lr}
+; CHECK-NEXT:push {r11, lr}
+; CHECK-NEXT:.pad #8
+; CHECK-NEXT:sub sp, sp, #8
+; CHECK-NEXT:mov r1, #6
+; CHECK-NEXT:mov r0, #5
+; CHECK-NEXT:strd r0, r1, [sp]
+; CHECK-NEXT:mov r0, #1
+; CHECK-NEXT:mov r1, #2
+; CHECK-NEXT:mov r2, #3
+; CHECK-NEXT:mov r3, #4
+; CHECK-NEXT:bl many_args_callee
+; CHECK-NEXT:add sp, sp, #8
+; CHECK-NEXT:pop {r11, pc}
+  %ret = tail call i32 @many_args_callee(i32 1, i32 2, i32 3, i32 4, i32 5, 
i32 6)
+  ret i32 %ret
+}
+
+declare void @sret_callee(ptr sret({ double, double }) align 8)
+
+; Functions which return by sret can be tail-called because the incoming sret
+; pointer gets passed through to the callee.
+define void @sret_caller_tail(ptr sret({ double, double }) align 8 %result) {
+; CHECK-LABEL: sret_caller_tail:
+; CHECK:   @ %bb.0: @ %entry
+; CHECK-NEXT:b sret_callee
+entry:
+  tail call void @sret_callee(ptr sret({ double, double }) align 8 %result)
+  ret void
+}
+
+define void @sret_caller_musttail(ptr sret({ double, double }) align 8 
%result) {
+; CHECK-LABEL: sret_caller_musttail:
+; CHECK:   @ %bb.0: @ %entry
+; CHECK-NEXT:b sret_callee
+entry:
+  musttail call void @sret_callee(ptr sret({ double, double }) align 8 %result)
+  ret void
+}
+
+; Clang only uses byval for arguments of 65 bytes or larger, but we test with a
+; 20 byte struct to keep the tests more readable. This size was chosen to still
+; make sure that it will be split between registers and the stack, to test all
+; of the interesting code paths in the backend.
+%twenty_bytes = type { [5 x i32] }
+declare void @large_callee(%twenty_bytes* byval(%twenty_bytes) align 4)
+
+; Functions with byval parameters can be tail-called, because the value is
+; actually passed in registers and the stack in the same way for the caller and
+; callee. Within @large_caller the first 16 bytes of the argument are spilled
+; to the loc

[clang] [clang-format] Add an option to control indentation of `export { ... }` (PR #110381)

2024-10-08 Thread via cfe-commits


@@ -26588,10 +26613,7 @@ TEST_F(FormatTest, Cpp20ModulesSupport) {
"  int foo;\n"
"};",
Style);
-  verifyFormat("export {\n"
-   "  int foo;\n"
-   "};",
-   Style);
+  verifyFormat("export { int foo; };", Style);

Sirraide wrote:

Yeah, makes sense. As far as I understand it, were were previously just parsing 
this as a compound statement, which afaik isn’t formatted on a single line by 
default, but maybe namespaces are, but I’m candidly not quite sure what’s 
causing this to be formatted on one line... I think this has something to do 
with the fact that I used `parseBlock` for this, but I’ll have to look into it 
a bit more.

Do we want a separate option for this (e.g. something like 
`AllowShortExportBlocksOnASingleLine`) or should that just fall under 
`AllowShortBlocksOnASingleLine`?

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


[clang] [llvm] [clang][LLVM Demangler] Add an assertion that validates that all mang… (PR #111391)

2024-10-08 Thread Ilya Biryukov via cfe-commits

ilya-biryukov wrote:

Sorry for jumping in late.

I think Erich is on point that having a flag that controls an assertion is a 
bit of a red flag as we are mixing build configuration and runtime 
configuration.

It is at least unusual and may cause confusion.

After thinking about this a bit more, should we maybe go all-in on one of the 
approaches?
- either use build configuration: add a new build flag that controls this 
assertion. Only assert when assertions are enabled and the new build flag is 
defined.
- or use runtime configure always, e.g. add diagnostics for names that can't be 
demangled. It should make finding those issues much easier (one can run the 
compiler to produce a list of names that can't be demangled with locations 
pointing at code that helps to identify where those names come from).


I would probably vouch for the second approach. The only downside that I see is 
that we have to explore the warning flag to users (right?) and this is 
something that should be internal (-cc1).

What do people think of that proposal?



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


[clang-tools-extra] [clangd] Harden incomingCalls() against possible misinterpretation of a range as pertaining to the wrong file (PR #111616)

2024-10-08 Thread Nathan Ridge via cfe-commits


@@ -2292,9 +2289,26 @@ incomingCalls(const CallHierarchyItem &Item, const 
SymbolIndex *Index) {
   Index->lookup(ContainerLookup, [&](const Symbol &Caller) {
 auto It = CallsIn.find(Caller.ID);
 assert(It != CallsIn.end());
-if (auto CHI = symbolToCallHierarchyItem(Caller, Item.uri.file()))
+if (auto CHI = symbolToCallHierarchyItem(Caller, Item.uri.file())) {
+  SymbolLocation CallerLoc =
+  Caller.Definition ? Caller.Definition : Caller.CanonicalDeclaration;
+  std::vector FromRanges;
+  for (const SymbolLocation &L : It->second) {
+if (StringRef{L.FileURI} != StringRef{CallerLoc.FileURI}) {
+  elog("incomingCalls: call location not in same file as caller, this "
+   "is unexpected");
+  continue;
+}
+Range R;

HighCommander4 wrote:

Note: I didn't use `indexToLSPLocation()` here because the `URI::resolve` 
operation that it does seems like unnecessary work here. I could factor out the 
part that converts the range into a function to avoid duplicating it here.

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


[clang-tools-extra] [clangd] Harden incomingCalls() against possible misinterpretation of a range as pertaining to the wrong file (PR #111616)

2024-10-08 Thread Nathan Ridge via cfe-commits


@@ -2292,9 +2289,26 @@ incomingCalls(const CallHierarchyItem &Item, const 
SymbolIndex *Index) {
   Index->lookup(ContainerLookup, [&](const Symbol &Caller) {
 auto It = CallsIn.find(Caller.ID);
 assert(It != CallsIn.end());
-if (auto CHI = symbolToCallHierarchyItem(Caller, Item.uri.file()))
+if (auto CHI = symbolToCallHierarchyItem(Caller, Item.uri.file())) {
+  SymbolLocation CallerLoc =
+  Caller.Definition ? Caller.Definition : Caller.CanonicalDeclaration;
+  std::vector FromRanges;
+  for (const SymbolLocation &L : It->second) {
+if (StringRef{L.FileURI} != StringRef{CallerLoc.FileURI}) {
+  elog("incomingCalls: call location not in same file as caller, this "

HighCommander4 wrote:

Should we assert as well?

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


[clang] [lld] [lld][LoongArch] Enable relaxation when --relax option is passed (PR #111488)

2024-10-08 Thread Fangrui Song via cfe-commits

https://github.com/MaskRay edited 
https://github.com/llvm/llvm-project/pull/111488
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[clang] [lld] [lld][LoongArch] Enable relaxation when --relax option is passed (PR #111488)

2024-10-08 Thread Fangrui Song via cfe-commits


@@ -1462,6 +1462,8 @@ template  void 
Writer::finalizeAddressDependentContent() {
   for (;;) {
 bool changed = ctx.target->needsThunks
? tc.createThunks(pass, ctx.outputSections)
+   : ctx.arg.emachine == EM_LOONGARCH && !ctx.arg.relax

MaskRay wrote:

Adding `ctx.arg.relax` to every place is not acceptable. You could change 
`ctx.arg.relax` to be always false for loongarch, though.

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


[clang] [lld] [lld][LoongArch] Enable relaxation when --relax option is passed (PR #111488)

2024-10-08 Thread Fangrui Song via cfe-commits


@@ -134,6 +134,13 @@ void loongarch::getLoongArchTargetFeatures(const Driver &D,
   (!Args.hasArgNoClaim(clang::driver::options::OPT_march_EQ)))
 Features.push_back("+lsx");
 
+  // -mrelax is default, unless -mno-relax is specified.

MaskRay wrote:


This code self explains and the comment is not necessary.

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


[clang] [lld] [lld][LoongArch] Enable relaxation when --relax option is passed (PR #111488)

2024-10-08 Thread Fangrui Song via cfe-commits

https://github.com/MaskRay commented:

We split clang and lld changes.


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


[clang] [clang] WIP: Warn on mismatched RequiresCapability attributes (PR #67520)

2024-10-08 Thread Timm Baeder via cfe-commits

https://github.com/tbaederr updated 
https://github.com/llvm/llvm-project/pull/67520

>From 55efd18bb177150a1fd170cb1535e225854967a6 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Timm=20B=C3=A4der?= 
Date: Thu, 20 Jun 2024 07:39:20 +0200
Subject: [PATCH] Warn on RequiresCapability attribute mismatch

---
 .../clang/Analysis/Analyses/ThreadSafety.h|  3 +++
 .../clang/Basic/DiagnosticSemaKinds.td|  4 ++-
 clang/lib/Analysis/ThreadSafety.cpp   | 25 +++
 clang/lib/Sema/AnalysisBasedWarnings.cpp  | 12 +
 .../SemaCXX/warn-thread-safety-analysis.cpp   | 10 
 5 files changed, 48 insertions(+), 6 deletions(-)

diff --git a/clang/include/clang/Analysis/Analyses/ThreadSafety.h 
b/clang/include/clang/Analysis/Analyses/ThreadSafety.h
index 0866b09bab2995..8211f55b088906 100644
--- a/clang/include/clang/Analysis/Analyses/ThreadSafety.h
+++ b/clang/include/clang/Analysis/Analyses/ThreadSafety.h
@@ -230,6 +230,9 @@ class ThreadSafetyHandler {
   /// Warn that there is a cycle in acquired_before/after dependencies.
   virtual void handleBeforeAfterCycle(Name L1Name, SourceLocation Loc) {}
 
+  virtual void handleAttributeMismatch(const NamedDecl *D1,
+   const NamedDecl *D2) {}
+
   /// Called by the analysis when starting analysis of a function.
   /// Used to issue suggestions for changes to annotations.
   virtual void enterFunction(const FunctionDecl *FD) {}
diff --git a/clang/include/clang/Basic/DiagnosticSemaKinds.td 
b/clang/include/clang/Basic/DiagnosticSemaKinds.td
index 583475327c5227..b57a2d6c899f8e 100644
--- a/clang/include/clang/Basic/DiagnosticSemaKinds.td
+++ b/clang/include/clang/Basic/DiagnosticSemaKinds.td
@@ -4031,7 +4031,9 @@ def warn_acquired_before : Warning<
 def warn_acquired_before_after_cycle : Warning<
   "cycle in acquired_before/after dependencies, starting with '%0'">,
   InGroup, DefaultIgnore;
-
+def warn_attribute_mismatch : Warning<
+  "attribute mismatch between function declarations of %0">,
+  InGroup, DefaultIgnore;
 
 // Thread safety warnings negative capabilities
 def warn_acquire_requires_negative_cap : Warning<
diff --git a/clang/lib/Analysis/ThreadSafety.cpp 
b/clang/lib/Analysis/ThreadSafety.cpp
index 5577f45aa5217f..2438d2af9df630 100644
--- a/clang/lib/Analysis/ThreadSafety.cpp
+++ b/clang/lib/Analysis/ThreadSafety.cpp
@@ -1073,6 +1073,8 @@ class ThreadSafetyAnalyzer {
ProtectedOperationKind POK);
   void checkPtAccess(const FactSet &FSet, const Expr *Exp, AccessKind AK,
  ProtectedOperationKind POK);
+
+  void checkMismatchedFunctionAttrs(const NamedDecl *ND);
 };
 
 } // namespace
@@ -2263,6 +2265,27 @@ static bool neverReturns(const CFGBlock *B) {
   return false;
 }
 
+void ThreadSafetyAnalyzer::checkMismatchedFunctionAttrs(const NamedDecl *ND) {
+  auto collectCapabilities = [&](const Decl *D) {
+CapExprSet Caps;
+for (const auto *A : D->specific_attrs()) {
+  for (const Expr *E : A->args())
+Caps.push_back_nodup(SxBuilder.translateAttrExpr(E, nullptr));
+}
+return Caps;
+  };
+
+  auto NDArgs = collectCapabilities(ND);
+  for (const Decl *D = ND->getPreviousDecl(); D; D = D->getPreviousDecl()) {
+auto DArgs = collectCapabilities(D);
+
+for (const auto &[A, B] : zip_longest(NDArgs, DArgs)) {
+  if (!A || !B || !A->equals(*B))
+Handler.handleAttributeMismatch(ND, cast(D));
+}
+  }
+}
+
 /// Check a function's CFG for thread-safety violations.
 ///
 /// We traverse the blocks in the CFG, compute the set of mutexes that are held
@@ -2282,6 +2305,8 @@ void 
ThreadSafetyAnalyzer::runAnalysis(AnalysisDeclContext &AC) {
   const NamedDecl *D = walker.getDecl();
   CurrentFunction = dyn_cast(D);
 
+  checkMismatchedFunctionAttrs(D);
+
   if (D->hasAttr())
 return;
 
diff --git a/clang/lib/Sema/AnalysisBasedWarnings.cpp 
b/clang/lib/Sema/AnalysisBasedWarnings.cpp
index 6496a33b8f5a50..cdec30cf135fd7 100644
--- a/clang/lib/Sema/AnalysisBasedWarnings.cpp
+++ b/clang/lib/Sema/AnalysisBasedWarnings.cpp
@@ -2073,6 +2073,18 @@ class ThreadSafetyReporter : public 
clang::threadSafety::ThreadSafetyHandler {
 Warnings.emplace_back(std::move(Warning), getNotes());
   }
 
+  void handleAttributeMismatch(const NamedDecl *ThisDecl,
+   const NamedDecl *PrevDecl) override {
+PartialDiagnosticAt Warning(ThisDecl->getLocation(),
+S.PDiag(diag::warn_attribute_mismatch)
+<< ThisDecl);
+Warnings.emplace_back(std::move(Warning), getNotes());
+
+PartialDiagnosticAt Note(PrevDecl->getLocation(),
+ S.PDiag(diag::note_previous_decl) << PrevDecl);
+Warnings.emplace_back(std::move(Note), getNotes());
+  }
+
   void enterFunction(const FunctionDecl* FD) override {
 CurrentFunction = FD;
   }
diff --git a/clang/test/SemaCXX/warn-thread-safety-analysis.cpp 
b/clang/test/SemaCXX/warn

[clang] [clang] WIP: Warn on mismatched RequiresCapability attributes (PR #67520)

2024-10-08 Thread Timm Baeder via cfe-commits
Timm =?utf-8?q?Bäder?= ,
Timm =?utf-8?q?Bäder?= ,
Timm =?utf-8?q?Bäder?= ,
Timm =?utf-8?q?Bäder?= ,
Timm =?utf-8?q?Bäder?= ,
Timm =?utf-8?q?Bäder?= ,
Timm =?utf-8?q?Bäder?= 
Message-ID:
In-Reply-To: 



@@ -2249,7 +2249,7 @@ void fooF1(Foo *f) EXCLUSIVE_LOCKS_REQUIRED(f->mu_) {
   f->a = 1;
 }
 
-void fooF2(Foo *f);
+void fooF2(Foo *f); // expected-warning {{attribute mismatch between function 
declarations of 'fooF2'}}
 void fooF2(Foo *f) EXCLUSIVE_LOCKS_REQUIRED(f->mu_) {

tbaederr wrote:

I guess that would make a little more sense, but swapping them also causes the 
note to not get emitted somehow.

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


[clang] [HLSL] Make HLSLAttributedResourceType canonical and add code paths to convert HLSL types to DirectX target types (PR #110327)

2024-10-08 Thread Helena Kotas via cfe-commits


@@ -3437,6 +3437,9 @@ static void encodeTypeForFunctionPointerAuth(const 
ASTContext &Ctx,
 OS << II->getLength() << II->getName();
 return;
   }
+  case Type::HLSLAttributedResource:

hekota wrote:

The other "should never get here"' is in a different switch statement. I will 
update the message to match.

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


[clang] [HLSL] Make HLSLAttributedResourceType canonical and add code paths to convert HLSL types to DirectX target types (PR #110327)

2024-10-08 Thread Helena Kotas via cfe-commits


@@ -13672,6 +13690,9 @@ static QualType getCommonNonSugarTypeNode(ASTContext 
&Ctx, const Type *X,
 TX->getDepth(), TX->getIndex(), TX->isParameterPack(),
 getCommonDecl(TX->getDecl(), TY->getDecl()));
   }
+  case Type::HLSLAttributedResource: {

hekota wrote:

I don't think this type should be sugared. I've added it to the diet types 
above.

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


[clang] [-Wunsafe-buffer-usage] Add user documentation. (PR #111624)

2024-10-08 Thread Artem Dergachev via cfe-commits

https://github.com/haoNoQ created 
https://github.com/llvm/llvm-project/pull/111624

This is an attempt to finally land the documentation that I initially wrote in 
https://reviews.llvm.org/D136811 - which doubled as RFC - and I sincerely 
apologize for not doing this sooner.

I've rewritten most of it in order to accurately reflect the current state of 
things, what's ready and what's not. The speculative/optimistic parts that 
haven't yet materialized were reduced significantly and moved into the "Future 
Work" section. In particular, since fixits aren't ready for everyday use yet, 
and even the specific approach we're going to take is still in motion, I 
decided not to speculate about where it ultimately lands.

The programming model is now described in more detail, in a more modern way. 
I've added some information about the latest improvements such as the support 
for `[[clang::unsafe_buffer_usage]]` on struct members. We now also have a 
chance to refer the users to the up-to-date libc++ hardening documentation page.

I'm very open to all sorts of suggestions. I'll do another round of 
proofreading later this week too.

@rapidsna: I'm referring the C users to the `-fbounds-safety` documentation but 
I understand that it is probably not ready for everyday use yet. Please let me 
know if I need to phrase this differently. Also please let me know if you want 
me to update the `-fbounds-safety` page to send the C++ people back to our page.

>From b5c9082e36efcc7be2cabc73c985749f2fd41725 Mon Sep 17 00:00:00 2001
From: Artem Dergachev 
Date: Tue, 8 Oct 2024 20:24:00 -0700
Subject: [PATCH] [-Wunsafe-buffer-usage] Add user documentation.

---
 clang/docs/SafeBuffers.rst | 585 +
 clang/docs/index.rst   |   1 +
 2 files changed, 586 insertions(+)
 create mode 100644 clang/docs/SafeBuffers.rst

diff --git a/clang/docs/SafeBuffers.rst b/clang/docs/SafeBuffers.rst
new file mode 100644
index 00..124f73799c72cb
--- /dev/null
+++ b/clang/docs/SafeBuffers.rst
@@ -0,0 +1,585 @@
+
+C++ Safe Buffers
+
+
+.. contents::
+   :local:
+
+
+Introduction
+
+
+Clang can be used to harden your C++ code against buffer overflows, an 
otherwise
+common security issue with C-based languages.
+
+The solution described in this document is an integrated programming model as
+it combines:
+
+- a family of opt-in Clang warnings (``-Wunsafe-buffer-usage``) emitted at
+  during compilation to help you update your code to encapsulate and propagate
+  the bounds information associated with pointers;
+- runtime assertions implemented as part of
+  (`libc++ hardening modes `_)
+  that eliminate undefined behavior as long as the coding convention
+  is followed and the bounds information is therefore available and correct.
+
+The goal of this work is to enable development of bounds-safe C++ code. It is
+not a "push-button" solution; depending on your codebase's existing
+coding style, significant (even if largely mechanical) changes to your code
+may be necessary. However, it allows you to achieve valuable safety guarantees
+on security-critical parts of your codebase.
+
+This solution is under active development. It is already useful for its purpose
+but more work is being done to improve ergonomics and safety guarantees
+and reduce adoption costs.
+
+The solution aligns in spirit with the "Ranges" safety profile
+that was `proposed 
`_
+by Bjarne Stroustrup for standardization alongside other C++ safety features.
+
+
+Pre-Requisites
+==
+
+In order to achieve bounds safety, your codebase needs to have access to
+well-encapsulated bounds-safe container, view, and iterator types.
+If your project uses libc++, standard container and view types such as
+``std::vector`` and ``std::span`` can be made bounds-safe by enabling
+the "fast" `hardening mode `_
+(passing ``-D_LIBCPP_HARDENING_MODE=_LIBCPP_HARDENING_MODE_FAST``) to your
+compiler) or any of the stricter hardening modes.
+
+In order to harden iterators, you'll need to also obtain a libc++ binary
+built with ``_LIBCPP_ABI_BOUNDED_ITERATORS`` -- which is a libc++ ABI setting
+that needs to be set for your entire target platform if you need to maintain
+binary compatibility with the rest of the platform.
+
+A relatively fresh version of C++ is recommended. In particular, the very 
useful
+standard view class ``std::span`` requires C++20.
+
+Other implementations of the C++ standard library may provide different
+flags to enable such hardening hardening.
+
+If you're using custom containers and views, they will need to be hardened
+this way as well, but you don't necessarily need to do this ahead of time.
+
+This approach can theoretically be applied to plain C codebases,
+assuming that safe primitives are developed to encapsulate all buffe

[clang] [-Wunsafe-buffer-usage] Add user documentation. (PR #111624)

2024-10-08 Thread via cfe-commits

llvmbot wrote:




@llvm/pr-subscribers-clang

Author: Artem Dergachev (haoNoQ)


Changes

This is an attempt to finally land the documentation that I initially wrote in 
https://reviews.llvm.org/D136811 - which doubled as RFC - and I sincerely 
apologize for not doing this sooner.

I've rewritten most of it in order to accurately reflect the current state of 
things, what's ready and what's not. The speculative/optimistic parts that 
haven't yet materialized were reduced significantly and moved into the "Future 
Work" section. In particular, since fixits aren't ready for everyday use yet, 
and even the specific approach we're going to take is still in motion, I 
decided not to speculate about where it ultimately lands.

The programming model is now described in more detail, in a more modern way. 
I've added some information about the latest improvements such as the support 
for `[[clang::unsafe_buffer_usage]]` on struct members. We now also have a 
chance to refer the users to the up-to-date libc++ hardening documentation page.

I'm very open to all sorts of suggestions. I'll do another round of 
proofreading later this week too.

@rapidsna: I'm referring the C users to the `-fbounds-safety` 
documentation but I understand that it is probably not ready for everyday use 
yet. Please let me know if I need to phrase this differently. Also please let 
me know if you want me to update the `-fbounds-safety` page to send the C++ 
people back to our page.

---

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


2 Files Affected:

- (added) clang/docs/SafeBuffers.rst (+585) 
- (modified) clang/docs/index.rst (+1) 


``diff
diff --git a/clang/docs/SafeBuffers.rst b/clang/docs/SafeBuffers.rst
new file mode 100644
index 00..124f73799c72cb
--- /dev/null
+++ b/clang/docs/SafeBuffers.rst
@@ -0,0 +1,585 @@
+
+C++ Safe Buffers
+
+
+.. contents::
+   :local:
+
+
+Introduction
+
+
+Clang can be used to harden your C++ code against buffer overflows, an 
otherwise
+common security issue with C-based languages.
+
+The solution described in this document is an integrated programming model as
+it combines:
+
+- a family of opt-in Clang warnings (``-Wunsafe-buffer-usage``) emitted at
+  during compilation to help you update your code to encapsulate and propagate
+  the bounds information associated with pointers;
+- runtime assertions implemented as part of
+  (`libc++ hardening modes `_)
+  that eliminate undefined behavior as long as the coding convention
+  is followed and the bounds information is therefore available and correct.
+
+The goal of this work is to enable development of bounds-safe C++ code. It is
+not a "push-button" solution; depending on your codebase's existing
+coding style, significant (even if largely mechanical) changes to your code
+may be necessary. However, it allows you to achieve valuable safety guarantees
+on security-critical parts of your codebase.
+
+This solution is under active development. It is already useful for its purpose
+but more work is being done to improve ergonomics and safety guarantees
+and reduce adoption costs.
+
+The solution aligns in spirit with the "Ranges" safety profile
+that was `proposed 
`_
+by Bjarne Stroustrup for standardization alongside other C++ safety features.
+
+
+Pre-Requisites
+==
+
+In order to achieve bounds safety, your codebase needs to have access to
+well-encapsulated bounds-safe container, view, and iterator types.
+If your project uses libc++, standard container and view types such as
+``std::vector`` and ``std::span`` can be made bounds-safe by enabling
+the "fast" `hardening mode `_
+(passing ``-D_LIBCPP_HARDENING_MODE=_LIBCPP_HARDENING_MODE_FAST``) to your
+compiler) or any of the stricter hardening modes.
+
+In order to harden iterators, you'll need to also obtain a libc++ binary
+built with ``_LIBCPP_ABI_BOUNDED_ITERATORS`` -- which is a libc++ ABI setting
+that needs to be set for your entire target platform if you need to maintain
+binary compatibility with the rest of the platform.
+
+A relatively fresh version of C++ is recommended. In particular, the very 
useful
+standard view class ``std::span`` requires C++20.
+
+Other implementations of the C++ standard library may provide different
+flags to enable such hardening hardening.
+
+If you're using custom containers and views, they will need to be hardened
+this way as well, but you don't necessarily need to do this ahead of time.
+
+This approach can theoretically be applied to plain C codebases,
+assuming that safe primitives are developed to encapsulate all buffer accesses,
+acting as "hardened custom containers" to replace raw pointers.
+However, such approach would be very unergonomic in C, and saf

[clang] [Clang][perf-training] Do build of libLLVMSupport for perf training (PR #111625)

2024-10-08 Thread Tom Stellard via cfe-commits

https://github.com/tstellar created 
https://github.com/llvm/llvm-project/pull/111625

This adds a build of the libLLVMSupport to the lit suite that is used for 
generating profile data.  This helps to improve both PGO and BOLT optimization 
of clang over the existing hello world training program.

I considered building all of LLVM instead of just libLLVMSupport, but there is 
only a marginal increase in performance for PGO only builds when training with 
a build of all of LLVM, and I didn't think it was enough to justify the 
increased build times given that it is the default configuration.

The benchmark[1] I did showed that using libLLVMSupport for training gives a 
1.35 +- 0.02 speed up for clang optimized with PGO + BOLT vs just 1.05 +- 0.01 
speed up when training with hello world.

For comparison, training with a full LLVM build gave a speed up of 1.35 +- 0.1.

Raw data:

| PGO Training | BOLT Training | Speed Up | Error Range |
|  | - |  | --- |
| LLVM Support | LLVM Support  | 1.35 | 0.02|
| LLVM All | LLVM All  | 1.34 | 0.01|
| LLVM Support | Hello World   | 1.29 | 0.02|
| LLVM All | PGO-ONLY  | 1.27 | 0.02|
| LLVM Support | PGO-ONLY  | 1.22 | 0.02|
| Hello World  | Hello World   | 1.05 | 0.01|
| Hello World  | PGO-ONLY  | 1.03 | 0.01|

[1] Benchmark was compiling SemaDecl.cpp

>From 40efbcf0fd348625c892453d915eb7601adda917 Mon Sep 17 00:00:00 2001
From: Tom Stellard 
Date: Sat, 5 Oct 2024 17:17:33 +
Subject: [PATCH] [Clang][perf-training] Do build of libLLVMSupport for perf
 training

This adds a build of the libLLVMSupport to the lit suite that is used
for generating profile data.  This helps to improve both PGO and BOLT
optimization of clang over the existing hello world training program.

I considered building all of LLVM instead of just libLLVMSupport, but
there is only a marginal increase in performance for PGO only builds
when training with a build of all of LLVM, and I didn't think it was
enough to justify the increased build times given that it is the default
configuration.

The benchmark[1] I did showed that using libLLVMSupport for training
gives a 1.35 +- 0.02 speed up for clang optimized with PGO + BOLT
vs just 1.05 +- 0.01 speed up when training with hello world.

For comparison, training with a full LLVM build gave a speed up of
1.35 +- 0.1.

Raw data:

| PGO Training | BOLT Training | Speed Up | Error Range |
|  | - |  | --- |
| LLVM Support | LLVM Support  | 1.35 | 0.02|
| LLVM All | LLVM All  | 1.34 | 0.01|
| LLVM Support | Hello World   | 1.29 | 0.02|
| LLVM All | PGO-ONLY  | 1.27 | 0.02|
| LLVM Support | PGO-ONLY  | 1.22 | 0.02|
| Hello World  | Hello World   | 1.05 | 0.01|
| Hello World  | PGO-ONLY  | 1.03 | 0.01|

[1] Benchmark was compiling SemaDecl.cpp
---
 clang/utils/perf-training/bolt.lit.cfg| 3 +++
 clang/utils/perf-training/bolt.lit.site.cfg.in| 3 +++
 clang/utils/perf-training/lit.cfg | 6 +-
 clang/utils/perf-training/lit.site.cfg.in | 3 +++
 clang/utils/perf-training/llvm-support/build.test | 2 ++
 5 files changed, 16 insertions(+), 1 deletion(-)
 create mode 100644 clang/utils/perf-training/llvm-support/build.test

diff --git a/clang/utils/perf-training/bolt.lit.cfg 
b/clang/utils/perf-training/bolt.lit.cfg
index 0e81a5501e9fcf..1d0cf9a8a17a8e 100644
--- a/clang/utils/perf-training/bolt.lit.cfg
+++ b/clang/utils/perf-training/bolt.lit.cfg
@@ -49,3 +49,6 @@ config.substitutions.append(("%clang_cpp", f" {config.clang} 
--driver-mode=g++ "
 config.substitutions.append(("%clang_skip_driver", config.clang))
 config.substitutions.append(("%clang", config.clang))
 config.substitutions.append(("%test_root", config.test_exec_root))
+config.substitutions.append(('%cmake_generator', config.cmake_generator))
+config.substitutions.append(('%cmake', config.cmake_exe))
+config.substitutions.append(('%llvm_src_dir', config.llvm_src_dir))
diff --git a/clang/utils/perf-training/bolt.lit.site.cfg.in 
b/clang/utils/perf-training/bolt.lit.site.cfg.in
index 54de12701c1ae9..3de5026e4792ae 100644
--- a/clang/utils/perf-training/bolt.lit.site.cfg.in
+++ b/clang/utils/perf-training/bolt.lit.site.cfg.in
@@ -11,6 +11,9 @@ config.python_exe = "@Python3_EXECUTABLE@"
 config.clang_obj_root = path(r"@CLANG_BINARY_DIR@")
 config.clang_bolt_mode = "@CLANG_BOLT@"
 config.clang_bolt_name = "@CLANG_BOLT_INSTRUMENTED@"
+config.cmake_exe = "@CMAKE_COMMAND@"
+config.llvm_src_dir ="@CMAKE_SOURCE_DIR@"
+config.cmake_generator ="@CMAKE_GENERATOR@"
 
 # Let the main config do the real work.
 lit_config.load_config(config, 
"@CLANG_SOURCE_DIR@/utils/perf-training/bolt.lit.cfg")
diff --git a/clang/utils/perf-training/lit.cfg 
b/clang/utils/perf-training/lit.cfg
index 0bd0

[clang] [llvm] [CGData][ThinLTO] Global Outlining with Two-CodeGen Rounds (PR #90933)

2024-10-08 Thread Teresa Johnson via cfe-commits


@@ -1513,6 +1522,171 @@ class InProcessThinBackend : public ThinBackendProc {
 return Error::success();
   }
 };
+
+/// This backend is utilized in the first round of a two-codegen round process.
+/// It first saves optimized bitcode files to disk before the codegen process
+/// begins. After codegen, it stores the resulting object files in a scratch
+/// buffer. Note the codegen data stored in the scratch buffer will be 
extracted
+/// and merged in the subsequent step.
+class FirstRoundThinBackend : public InProcessThinBackend {
+  AddStreamFn IRAddStream;
+  FileCache IRCache;
+
+public:
+  FirstRoundThinBackend(
+  const Config &Conf, ModuleSummaryIndex &CombinedIndex,
+  ThreadPoolStrategy ThinLTOParallelism,
+  const DenseMap &ModuleToDefinedGVSummaries,
+  AddStreamFn CGAddStream, FileCache CGCache, AddStreamFn IRAddStream,
+  FileCache IRCache)
+  : InProcessThinBackend(Conf, CombinedIndex, ThinLTOParallelism,
+ ModuleToDefinedGVSummaries, 
std::move(CGAddStream),
+ std::move(CGCache), /*OnWrite=*/nullptr,
+ /*ShouldEmitIndexFiles=*/false,
+ /*ShouldEmitImportsFiles=*/false),
+IRAddStream(std::move(IRAddStream)), IRCache(std::move(IRCache)) {}
+
+  Error runThinLTOBackendThread(
+  AddStreamFn CGAddStream, FileCache CGCache, unsigned Task,
+  BitcodeModule BM, ModuleSummaryIndex &CombinedIndex,
+  const FunctionImporter::ImportMapTy &ImportList,
+  const FunctionImporter::ExportSetTy &ExportList,
+  const std::map 
&ResolvedODR,
+  const GVSummaryMapTy &DefinedGlobals,
+  MapVector &ModuleMap) override {
+auto RunThinBackend = [&](AddStreamFn CGAddStream,
+  AddStreamFn IRAddStream) {
+  LTOLLVMContext BackendContext(Conf);
+  Expected> MOrErr = 
BM.parseModule(BackendContext);
+  if (!MOrErr)
+return MOrErr.takeError();
+
+  return thinBackend(Conf, Task, CGAddStream, **MOrErr, CombinedIndex,
+ ImportList, DefinedGlobals, &ModuleMap,
+ Conf.CodeGenOnly, IRAddStream);
+};
+
+auto ModuleID = BM.getModuleIdentifier();
+// Like InProcessThinBackend, we produce index files as needed for
+// FirstRoundThinBackend. However, these files are not generated for
+// SecondRoundThinBackend.
+if (ShouldEmitIndexFiles) {
+  if (auto E = emitFiles(ImportList, ModuleID, ModuleID.str()))
+return E;
+}
+
+assert((CGCache.isValid() == IRCache.isValid()) &&
+   "Both caches for CG and IR should have matching availability");
+if (!CGCache.isValid() || !CombinedIndex.modulePaths().count(ModuleID) ||
+all_of(CombinedIndex.getModuleHash(ModuleID),
+   [](uint32_t V) { return V == 0; }))
+  // Cache disabled or no entry for this module in the combined index or
+  // no module hash.
+  return RunThinBackend(CGAddStream, IRAddStream);
+
+// Get CGKey for caching object in CGCache.
+std::string CGKey = computeLTOCacheKey(
+Conf, CombinedIndex, ModuleID, ImportList, ExportList, ResolvedODR,
+DefinedGlobals, CfiFunctionDefs, CfiFunctionDecls);
+Expected CacheCGAddStreamOrErr =
+CGCache(Task, CGKey, ModuleID);
+if (Error Err = CacheCGAddStreamOrErr.takeError())
+  return Err;
+AddStreamFn &CacheCGAddStream = *CacheCGAddStreamOrErr;
+
+// Get IRKey for caching (optimized) IR in IRCache with an extra ID.
+std::string IRKey = computeLTOCacheKey(

teresajohnson wrote:

It's a bit unfortunate to have to compute the whole cache key again but just 
with one extra ID added. I suppose an alternative would be to just rehash the 
CGKey with "IR".

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


[clang] [llvm] [CGData][ThinLTO] Global Outlining with Two-CodeGen Rounds (PR #90933)

2024-10-08 Thread Teresa Johnson via cfe-commits


@@ -0,0 +1,94 @@
+; This test verifies whether we can outline a singleton instance (i.e., an 
instance that does not repeat)

teresajohnson wrote:

This test seems like mostly an overlap of the caching test, with the exception 
of the regular LTO module interactions. Can you better describe that here?

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


[clang] [llvm] [CGData][ThinLTO] Global Outlining with Two-CodeGen Rounds (PR #90933)

2024-10-08 Thread Teresa Johnson via cfe-commits


@@ -1513,6 +1522,171 @@ class InProcessThinBackend : public ThinBackendProc {
 return Error::success();
   }
 };
+
+/// This backend is utilized in the first round of a two-codegen round process.
+/// It first saves optimized bitcode files to disk before the codegen process
+/// begins. After codegen, it stores the resulting object files in a scratch
+/// buffer. Note the codegen data stored in the scratch buffer will be 
extracted
+/// and merged in the subsequent step.
+class FirstRoundThinBackend : public InProcessThinBackend {
+  AddStreamFn IRAddStream;
+  FileCache IRCache;
+
+public:
+  FirstRoundThinBackend(
+  const Config &Conf, ModuleSummaryIndex &CombinedIndex,
+  ThreadPoolStrategy ThinLTOParallelism,
+  const DenseMap &ModuleToDefinedGVSummaries,
+  AddStreamFn CGAddStream, FileCache CGCache, AddStreamFn IRAddStream,
+  FileCache IRCache)
+  : InProcessThinBackend(Conf, CombinedIndex, ThinLTOParallelism,
+ ModuleToDefinedGVSummaries, 
std::move(CGAddStream),
+ std::move(CGCache), /*OnWrite=*/nullptr,
+ /*ShouldEmitIndexFiles=*/false,
+ /*ShouldEmitImportsFiles=*/false),
+IRAddStream(std::move(IRAddStream)), IRCache(std::move(IRCache)) {}
+
+  Error runThinLTOBackendThread(
+  AddStreamFn CGAddStream, FileCache CGCache, unsigned Task,
+  BitcodeModule BM, ModuleSummaryIndex &CombinedIndex,
+  const FunctionImporter::ImportMapTy &ImportList,
+  const FunctionImporter::ExportSetTy &ExportList,
+  const std::map 
&ResolvedODR,
+  const GVSummaryMapTy &DefinedGlobals,
+  MapVector &ModuleMap) override {
+auto RunThinBackend = [&](AddStreamFn CGAddStream,
+  AddStreamFn IRAddStream) {
+  LTOLLVMContext BackendContext(Conf);
+  Expected> MOrErr = 
BM.parseModule(BackendContext);
+  if (!MOrErr)
+return MOrErr.takeError();
+
+  return thinBackend(Conf, Task, CGAddStream, **MOrErr, CombinedIndex,
+ ImportList, DefinedGlobals, &ModuleMap,
+ Conf.CodeGenOnly, IRAddStream);
+};
+
+auto ModuleID = BM.getModuleIdentifier();
+// Like InProcessThinBackend, we produce index files as needed for
+// FirstRoundThinBackend. However, these files are not generated for
+// SecondRoundThinBackend.
+if (ShouldEmitIndexFiles) {
+  if (auto E = emitFiles(ImportList, ModuleID, ModuleID.str()))
+return E;
+}
+
+assert((CGCache.isValid() == IRCache.isValid()) &&
+   "Both caches for CG and IR should have matching availability");
+if (!CGCache.isValid() || !CombinedIndex.modulePaths().count(ModuleID) ||
+all_of(CombinedIndex.getModuleHash(ModuleID),
+   [](uint32_t V) { return V == 0; }))
+  // Cache disabled or no entry for this module in the combined index or
+  // no module hash.
+  return RunThinBackend(CGAddStream, IRAddStream);
+
+// Get CGKey for caching object in CGCache.
+std::string CGKey = computeLTOCacheKey(
+Conf, CombinedIndex, ModuleID, ImportList, ExportList, ResolvedODR,
+DefinedGlobals, CfiFunctionDefs, CfiFunctionDecls);
+Expected CacheCGAddStreamOrErr =
+CGCache(Task, CGKey, ModuleID);
+if (Error Err = CacheCGAddStreamOrErr.takeError())
+  return Err;
+AddStreamFn &CacheCGAddStream = *CacheCGAddStreamOrErr;
+
+// Get IRKey for caching (optimized) IR in IRCache with an extra ID.
+std::string IRKey = computeLTOCacheKey(
+Conf, CombinedIndex, ModuleID, ImportList, ExportList, ResolvedODR,
+DefinedGlobals, CfiFunctionDefs, CfiFunctionDecls, /*ExtraID=*/"IR");
+Expected CacheIRAddStreamOrErr =
+IRCache(Task, IRKey, ModuleID);
+if (Error Err = CacheIRAddStreamOrErr.takeError())
+  return Err;
+AddStreamFn &CacheIRAddStream = *CacheIRAddStreamOrErr;
+
+assert((CacheCGAddStream == nullptr) == (CacheIRAddStream == nullptr) &&
+   "Both CG and IR caching should be matched");
+if (CacheIRAddStream) {
+  LLVM_DEBUG(dbgs() << "[FirstRound] Cache Miss for "
+<< BM.getModuleIdentifier() << "\n");
+  return RunThinBackend(CacheCGAddStream, CacheIRAddStream);
+}
+
+return Error::success();
+  }
+};
+
+/// This backend operates in the second round of a two-codegen round process.
+/// It starts by reading the optimized bitcode files that were saved during the
+/// first round. The backend then executes the codegen only to further optimize
+/// the code, utilizing the codegen data merged from the first round. Finally,
+/// it writes the resulting object files as usual.
+class SecondRoundThinBackend : public InProcessThinBackend {
+  std::unique_ptr> IRFiles;
+  stable_hash CombinedCGDataHash;
+
+public:
+  SecondRoundThinBackend(
+  const Config &Conf, ModuleSummaryIndex &CombinedIndex,
+

[clang] [Clang][perf-training] Do build of libLLVMSupport for perf training (PR #111625)

2024-10-08 Thread via cfe-commits

llvmbot wrote:




@llvm/pr-subscribers-clang

Author: Tom Stellard (tstellar)


Changes

This adds a build of the libLLVMSupport to the lit suite that is used for 
generating profile data.  This helps to improve both PGO and BOLT optimization 
of clang over the existing hello world training program.

I considered building all of LLVM instead of just libLLVMSupport, but there is 
only a marginal increase in performance for PGO only builds when training with 
a build of all of LLVM, and I didn't think it was enough to justify the 
increased build times given that it is the default configuration.

The benchmark[1] I did showed that using libLLVMSupport for training gives a 
1.35 +- 0.02 speed up for clang optimized with PGO + BOLT vs just 1.05 +- 0.01 
speed up when training with hello world.

For comparison, training with a full LLVM build gave a speed up of 1.35 +- 0.1.

Raw data:

| PGO Training | BOLT Training | Speed Up | Error Range |
|  | - |  | --- |
| LLVM Support | LLVM Support  | 1.35 | 0.02|
| LLVM All | LLVM All  | 1.34 | 0.01|
| LLVM Support | Hello World   | 1.29 | 0.02|
| LLVM All | PGO-ONLY  | 1.27 | 0.02|
| LLVM Support | PGO-ONLY  | 1.22 | 0.02|
| Hello World  | Hello World   | 1.05 | 0.01|
| Hello World  | PGO-ONLY  | 1.03 | 0.01|

[1] Benchmark was compiling SemaDecl.cpp

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


5 Files Affected:

- (modified) clang/utils/perf-training/bolt.lit.cfg (+3) 
- (modified) clang/utils/perf-training/bolt.lit.site.cfg.in (+3) 
- (modified) clang/utils/perf-training/lit.cfg (+5-1) 
- (modified) clang/utils/perf-training/lit.site.cfg.in (+3) 
- (added) clang/utils/perf-training/llvm-support/build.test (+2) 


``diff
diff --git a/clang/utils/perf-training/bolt.lit.cfg 
b/clang/utils/perf-training/bolt.lit.cfg
index 0e81a5501e9fcf..1d0cf9a8a17a8e 100644
--- a/clang/utils/perf-training/bolt.lit.cfg
+++ b/clang/utils/perf-training/bolt.lit.cfg
@@ -49,3 +49,6 @@ config.substitutions.append(("%clang_cpp", f" {config.clang} 
--driver-mode=g++ "
 config.substitutions.append(("%clang_skip_driver", config.clang))
 config.substitutions.append(("%clang", config.clang))
 config.substitutions.append(("%test_root", config.test_exec_root))
+config.substitutions.append(('%cmake_generator', config.cmake_generator))
+config.substitutions.append(('%cmake', config.cmake_exe))
+config.substitutions.append(('%llvm_src_dir', config.llvm_src_dir))
diff --git a/clang/utils/perf-training/bolt.lit.site.cfg.in 
b/clang/utils/perf-training/bolt.lit.site.cfg.in
index 54de12701c1ae9..3de5026e4792ae 100644
--- a/clang/utils/perf-training/bolt.lit.site.cfg.in
+++ b/clang/utils/perf-training/bolt.lit.site.cfg.in
@@ -11,6 +11,9 @@ config.python_exe = "@Python3_EXECUTABLE@"
 config.clang_obj_root = path(r"@CLANG_BINARY_DIR@")
 config.clang_bolt_mode = "@CLANG_BOLT@"
 config.clang_bolt_name = "@CLANG_BOLT_INSTRUMENTED@"
+config.cmake_exe = "@CMAKE_COMMAND@"
+config.llvm_src_dir ="@CMAKE_SOURCE_DIR@"
+config.cmake_generator ="@CMAKE_GENERATOR@"
 
 # Let the main config do the real work.
 lit_config.load_config(config, 
"@CLANG_SOURCE_DIR@/utils/perf-training/bolt.lit.cfg")
diff --git a/clang/utils/perf-training/lit.cfg 
b/clang/utils/perf-training/lit.cfg
index 0bd06c0d44f650..b4527c602fc484 100644
--- a/clang/utils/perf-training/lit.cfg
+++ b/clang/utils/perf-training/lit.cfg
@@ -34,8 +34,12 @@ config.test_format = lit.formats.ShTest(use_lit_shell == "0")
 config.substitutions.append( ('%clang_cpp_skip_driver', ' %s %s %s ' % 
(cc1_wrapper, config.clang, sysroot_flags)))
 config.substitutions.append( ('%clang_cpp', ' %s --driver-mode=g++ %s ' % 
(config.clang, sysroot_flags)))
 config.substitutions.append( ('%clang_skip_driver', ' %s %s %s ' % 
(cc1_wrapper, config.clang, sysroot_flags)))
-config.substitutions.append( ('%clang', ' %s %s ' % (config.clang, 
sysroot_flags) ) )
+config.substitutions.append( ('%clang', '%s %s ' % (config.clang, 
sysroot_flags) ) )
 config.substitutions.append( ('%test_root', config.test_exec_root ) )
+config.substitutions.append( ('%cmake_generator', config.cmake_generator ) )
+config.substitutions.append( ('%cmake', config.cmake_exe ) )
+config.substitutions.append( ('%llvm_src_dir', config.llvm_src_dir ) )
 
+print(config.substitutions)
 config.environment['LLVM_PROFILE_FILE'] = 'perf-training-%4m.profraw'
 
diff --git a/clang/utils/perf-training/lit.site.cfg.in 
b/clang/utils/perf-training/lit.site.cfg.in
index fae93065a4edf2..9d279d552919ac 100644
--- a/clang/utils/perf-training/lit.site.cfg.in
+++ b/clang/utils/perf-training/lit.site.cfg.in
@@ -8,6 +8,9 @@ config.test_exec_root = "@CMAKE_CURRENT_BINARY_DIR@"
 config.test_source_root = "@CLANG_PGO_TRAINING_DATA@"
 config.target_triple = "@LLVM_TARGET_TRIPLE@"
 config.python_exe = "@Python3_EXECUTABLE@"
+config.cmake_exe = "@CMAKE_COMM

[clang] [Sema] Support negation/parens with __builtin_available (PR #111439)

2024-10-08 Thread Helena Kotas via cfe-commits

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

LGTM!

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


[clang] Switch DirectX Target to use the Itanium ABI (PR #111632)

2024-10-08 Thread Greg Roth via cfe-commits


@@ -1,35 +1,66 @@
-// RUN: %clang_cc1 -finclude-default-header -x hlsl -triple \
-// RUN:   dxil-pc-shadermodel6.3-library %s \
+// RUN: %clang_cc1 -finclude-default-header -triple 
dxil-pc-shadermodel6.3-library %s \
 // RUN:   -emit-llvm -disable-llvm-passes -o - | FileCheck %s
 
 int shl32(int V, int S) {
   return V << S;
 }
 
-// CHECK: define noundef i32 @"?shl32{{[@$?.A-Za-z0-9_]+}}"(i32 noundef %V, 
i32 noundef %S) #0 {
+// CHECK-LABEL: define noundef i32 @_Z5shl32ii(i32 noundef %V, i32 noundef %S) 
#0 {
 // CHECK-DAG:  %[[Masked:.*]] = and i32 %{{.*}}, 31
 // CHECK-DAG:  %{{.*}} = shl i32 %{{.*}}, %[[Masked]]
 
 int shr32(int V, int S) {
   return V >> S;
 }
 
-// CHECK: define noundef i32 @"?shr32{{[@$?.A-Za-z0-9_]+}}"(i32 noundef %V, 
i32 noundef %S) #0 {
+// CHECK-LABEL: define noundef i32 @_Z5shr32ii(i32 noundef %V, i32 noundef %S) 
#0 {
 // CHECK-DAG:  %[[Masked:.*]] = and i32 %{{.*}}, 31
 // CHECK-DAG:  %{{.*}} = ashr i32 %{{.*}}, %[[Masked]]
 
 int64_t shl64(int64_t V, int64_t S) {
   return V << S;
 }
 
-// CHECK: define noundef i64 @"?shl64{{[@$?.A-Za-z0-9_]+}}"(i64 noundef %V, 
i64 noundef %S) #0 {
+// CHECK-LABEL: define noundef i64 @_Z5shl64ll(i64 noundef %V, i64 noundef %S) 
#0 {
 // CHECK-DAG:  %[[Masked:.*]] = and i64 %{{.*}}, 63
 // CHECK-DAG:  %{{.*}} = shl i64 %{{.*}}, %[[Masked]]
 
 int64_t shr64(int64_t V, int64_t S) {
   return V >> S;
 }
 
-// CHECK: define noundef i64 @"?shr64{{[@$?.A-Za-z0-9_]+}}"(i64 noundef %V, 
i64 noundef %S) #0 {
+// CHECK-LABEL: define noundef i64 @_Z5shr64ll(i64 noundef %V, i64 noundef %S) 
#0 {
 // CHECK-DAG:  %[[Masked:.*]] = and i64 %{{.*}}, 63
 // CHECK-DAG:  %{{.*}} = ashr i64 %{{.*}}, %[[Masked]]
+
+uint shlu32(uint V, uint S) {
+  return V << S;
+}
+
+// CHECK-LABEL: define noundef i32 @_Z6shlu32jj(i32 noundef %V, i32 noundef 
%S) #0 {
+// CHECK-DAG:  %[[Masked:.*]] = and i32 %{{.*}}, 31
+// CHECK-DAG:  %{{.*}} = shl i32 %{{.*}}, %[[Masked]]
+
+uint shru32(uint V, uint S) {
+  return V >> S;
+}
+
+// CHECK-LABEL: define noundef i32 @_Z6shru32jj(i32 noundef %V, i32 noundef 
%S) #0 {
+// CHECK-DAG:  %[[Masked:.*]] = and i32 %{{.*}}, 31
+// CHECK-DAG:  %{{.*}} = lshr i32 %{{.*}}, %[[Masked]]
+
+uint64_t shlu64(uint64_t V, uint64_t S) {
+  return V << S;
+}
+
+// CHECK-LABEL: define noundef i64 @_Z6shlu64mm(i64 noundef %V, i64 noundef 
%S) #0 {
+// CHECK-DAG:  %[[Masked:.*]] = and i64 %{{.*}}, 63
+// CHECK-DAG:  %{{.*}} = shl i64 %{{.*}}, %[[Masked]]
+
+uint64_t shru64(uint64_t V, uint64_t S) {
+  return V >> S;
+}
+
+// CHECK-LABEL: define noundef i64 @_Z6shru64mm(i64 noundef %V, i64 noundef 
%S) #0 {
+// CHECK-DAG:  %[[Masked:.*]] = and i64 %{{.*}}, 63
+// CHECK-DAG:  %{{.*}} = lshr i64 %{{.*}}, %[[Masked]]

pow2clk wrote:

This is all incidental, I just thought we should test some logical shifts.

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


[clang] Switch DirectX Target to use the Itanium ABI (PR #111632)

2024-10-08 Thread Greg Roth via cfe-commits

https://github.com/pow2clk commented:

Just a few comments to explain the changes that aren't just mangling style 
changes.

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


[clang] Switch DirectX Target to use the Itanium ABI (PR #111632)

2024-10-08 Thread Greg Roth via cfe-commits


@@ -1,93 +1,96 @@
-// RUN: %clang_cc1 -std=hlsl2021 -finclude-default-header -x hlsl -triple \
-// RUN:   dxil-pc-shadermodel6.3-library %s -fnative-half-type \
-// RUN:   -emit-llvm -disable-llvm-passes -o - | FileCheck %s \ 
-// RUN:   --check-prefixes=CHECK,NATIVE_HALF
-// RUN: %clang_cc1 -std=hlsl2021 -finclude-default-header -x hlsl -triple \
-// RUN:   dxil-pc-shadermodel6.3-library %s -emit-llvm -disable-llvm-passes \
-// RUN:   -o - | FileCheck %s --check-prefixes=CHECK,NO_HALF
+// RUN: %clang_cc1 -finclude-default-header -triple 
dxil-pc-shadermodel6.3-library %s \
+// RUN:  -fnative-half-type -emit-llvm -disable-llvm-passes -o - | \
+// RUN:  FileCheck %s --check-prefixes=CHECK,NATIVE_HALF
+// RUN: %clang_cc1 -finclude-default-header -triple 
dxil-pc-shadermodel6.3-library %s \
+// RUN:  -emit-llvm -disable-llvm-passes -o - | \
+// RUN:  FileCheck %s --check-prefixes=CHECK,NO_HALF
 
 using hlsl::abs;
 
 #ifdef __HLSL_ENABLE_16_BIT
-// NATIVE_HALF: define noundef i16 @
+// NATIVE_HALF-LABEL: define noundef i16 @_Z16test_abs_int16_t

pow2clk wrote:

There was a lot of inconsistency in these sorts of checks. Some included more 
and some less. I tried to include enough to unambiguously identify the function 
in question.

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


[clang] Switch DirectX Target to use the Itanium ABI (PR #111632)

2024-10-08 Thread Greg Roth via cfe-commits


@@ -1,7 +1,7 @@
-// RUN: %clang_cc1 -triple dxil-pc-shadermodel6.0-compute -std=hlsl202x 
-emit-llvm -disable-llvm-passes %s -o - | FileCheck %s 
--check-prefixes=CS,NOINLINE,CHECK
-// RUN: %clang_cc1 -triple dxil-pc-shadermodel6.3-library -std=hlsl202x 
-emit-llvm -disable-llvm-passes %s -o - | FileCheck %s 
--check-prefixes=LIB,NOINLINE,CHECK
-// RUN: %clang_cc1 -triple dxil-pc-shadermodel6.0-compute -std=hlsl202x 
-emit-llvm -O0 %s -o - | FileCheck %s --check-prefixes=INLINE,CHECK
-// RUN: %clang_cc1 -triple dxil-pc-shadermodel6.3-library -std=hlsl202x 
-emit-llvm -O0 %s -o - | FileCheck %s --check-prefixes=INLINE,CHECK
+// RUN: %clang_cc1 -triple dxil-pc-shadermodel6.0-compute -emit-llvm 
-disable-llvm-passes %s -o - | FileCheck %s --check-prefixes=CS,NOINLINE,CHECK
+// RUN: %clang_cc1 -triple dxil-pc-shadermodel6.3-library -emit-llvm 
-disable-llvm-passes %s -o - | FileCheck %s --check-prefixes=LIB,NOINLINE,CHECK
+// RUN: %clang_cc1 -triple dxil-pc-shadermodel6.0-compute -emit-llvm -O0 %s -o 
- | FileCheck %s --check-prefixes=INLINE,CHECK
+// RUN: %clang_cc1 -triple dxil-pc-shadermodel6.3-library -emit-llvm -O0 %s -o 
- | FileCheck %s --check-prefixes=INLINE,CHECK

pow2clk wrote:

hlsl202x is the default now, so this flag is redundant.

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


[clang] Switch DirectX Target to use the Itanium ABI (PR #111632)

2024-10-08 Thread Greg Roth via cfe-commits


@@ -56,14 +55,12 @@ void main() {
 
 // CHECK-LABEL: define {{.*}}DoSilly
 // CHECK-NEXT:entry:
-// CHECK-NEXT: [[ResPtr:%.*]] = alloca ptr
 // CHECK-NEXT: [[ThisPtrAddr:%.*]] = alloca ptr
-// CHECK-NEXT: store ptr [[AggRes:%.*]], ptr [[ResPtr]]
 // CHECK-NEXT: store ptr {{.*}}, ptr [[ThisPtrAddr]]
 // CHECK-NEXT: [[ThisPtr:%.*]] = load ptr, ptr [[ThisPtrAddr]]
 // CHECK-NEXT: call void @llvm.memcpy.p0.p0.i32(ptr align 4 [[ThisPtr]], ptr 
align 4 [[Obj:%.*]], i32 8, i1 false)
 // CHECK-NEXT: [[FirstAddr:%.*]] = getelementptr inbounds nuw %struct.Pair, 
ptr [[ThisPtr]], i32 0, i32 0
 // CHECK-NEXT: [[First:%.*]] = load i32, ptr [[FirstAddr]]
 // CHECK-NEXT: [[FirstPlusTwo:%.*]] = add nsw i32 [[First]], 2
 // CHECK-NEXT: store i32 [[FirstPlusTwo]], ptr [[FirstAddr]]
-// CHECK-NEXT: call void @llvm.memcpy.p0.p0.i32(ptr align 4 [[AggRes]], ptr 
align 4 [[Obj]], i32 8, i1 false)
+// CHECK-NEXT: call void @llvm.memcpy.p0.p0.i32(ptr align 4 {{.*}}, ptr align 
4 [[Obj]], i32 8, i1 false)

pow2clk wrote:

I can't explain exactly why the `ResPtr` alloca was removed, but it was clearly 
unnecessary. The wildcard here represents the same location as was previously 
captured in `AggRes` and copied into `ResPtr`, but then `ResPtr` was never used.

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


[clang] Switch DirectX Target to use the Itanium ABI (PR #111632)

2024-10-08 Thread Greg Roth via cfe-commits


@@ -289,17 +289,19 @@ void setFour(inout int I) {
 // CHECK: [[B:%.*]] = alloca %struct.B
 // CHECK: [[Tmp:%.*]] = alloca i32
 
-// CHECK: [[BFLoad:%.*]] = load i32, ptr [[B]]
-// CHECK: [[BFshl:%.*]] = shl i32 [[BFLoad]], 24
-// CHECK: [[BFashr:%.*]] = ashr i32 [[BFshl]], 24
-// CHECK: store i32 [[BFashr]], ptr [[Tmp]]
+// CHECK: [[BFLoad:%.*]] = load i16, ptr [[B]]
+// CHECK: [[BFshl:%.*]] = shl i16 [[BFLoad]], 8
+// CHECK: [[BFashr:%.*]] = ashr i16 [[BFshl]], 8
+// CHECK: [[BFcast:%.*]] = sext i16 [[BFashr]] to i32
+// CHECK: store i32 [[BFcast]], ptr [[Tmp]]
 // CHECK: call void {{.*}}setFour{{.*}}(ptr noalias noundef nonnull align 4 
dereferenceable(4) [[Tmp]])
 // CHECK: [[RetVal:%.*]] = load i32, ptr [[Tmp]]
-// CHECK: [[BFLoad:%.*]] = load i32, ptr [[B]]
-// CHECK: [[BFValue:%.*]] = and i32 [[RetVal]], 255
-// CHECK: [[ZerodField:%.*]] = and i32 [[BFLoad]], -256
-// CHECK: [[BFSet:%.*]] = or i32 [[ZerodField]], [[BFValue]]
-// CHECK: store i32 [[BFSet]], ptr [[B]]
+// CHECK: [[TruncVal:%.*]] = trunc i32 [[RetVal]] to i16
+// CHECK: [[BFLoad:%.*]] = load i16, ptr [[B]]
+// CHECK: [[BFValue:%.*]] = and i16 [[TruncVal]], 255
+// CHECK: [[ZerodField:%.*]] = and i16 [[BFLoad]], -256
+// CHECK: [[BFSet:%.*]] = or i16 [[ZerodField]], [[BFValue]]
+// CHECK: store i16 [[BFSet]], ptr [[B]]

pow2clk wrote:

This is an instance of using smaller types where possible. Doing so introduced 
some additional commands.

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


[clang] Switch DirectX Target to use the Itanium ABI (PR #111632)

2024-10-08 Thread Greg Roth via cfe-commits


@@ -13,16 +13,16 @@ void InitBuf(RWBuffer buf) {
 }
 
 // CHECK-NOT: _Init_thread_epoch
-// CHECK: define internal void @"?main@@YAXXZ"
+// CHECK: define internal void @_Z4mainv
 // CHECK-NEXT: entry:
 // CHECK-NEXT: [[Tmp1:%.*]] = alloca %"class.hlsl::RWBuffer"
-// CHECK-NEXT: [[Tmp2:%.*]] = load i32, ptr
-// CHECK-NEXT: [[Tmp3:%.*]] = and i32 [[Tmp2]], 1
-// CHECK-NEXT: [[Tmp4:%.*]] = icmp eq i32 [[Tmp3]], 0
-// CHECK-NEXT: br i1 [[Tmp4]]
+// CHECK-NEXT: [[Tmp2:%.*]] = load i8, ptr @_ZGVZ4mainvE5mybuf
+// CHECK-NEXT: [[Tmp3:%.*]] = icmp eq i8 [[Tmp2]], 0
+// CHECK-NEXT: br i1 [[Tmp3]]
 // CHECK-NOT: _Init_thread_header
-// CHECK: init:
-// CHECK-NEXT: = or i32 [[Tmp2]], 1
+// CHECK: init.check:
+// CHECK-NEXT: call void @_ZN4hlsl8RWBufferIiEC1Ev
+// CHECK-NEXT: store i8 1, ptr @_ZGVZ4mainvE5mybuf

pow2clk wrote:

These changes represent a different, but equivalent way of protecting the 
one-time initialization of a static local variable

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


[clang] Switch DirectX Target to use the Itanium ABI (PR #111632)

2024-10-08 Thread Greg Roth via cfe-commits

https://github.com/pow2clk edited 
https://github.com/llvm/llvm-project/pull/111632
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


  1   2   3   4   5   >