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

Doug Wyatt via cfe-commits cfe-commits at lists.llvm.org
Sat Oct 5 09:34:43 PDT 2024


https://github.com/dougsonos updated https://github.com/llvm/llvm-project/pull/111224

>From 02398e6398892dac5d151a6e425bf107213e12a8 Mon Sep 17 00:00:00 2001
From: Doug Wyatt <dwyatt at apple.com>
Date: Fri, 4 Oct 2024 18:28:37 -0700
Subject: [PATCH 1/3] Effect analysis: correctly detect `(f ? a : b)` as
 nonblocking when a and b are.

---
 clang/lib/Sema/SemaFunctionEffects.cpp           | 11 +++++------
 clang/test/Sema/attr-nonblocking-constraints.cpp | 10 ++++++++++
 2 files changed, 15 insertions(+), 6 deletions(-)

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<FunctionProtoType>(); // 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..ff8caf0e573403 100644
--- a/clang/test/Sema/attr-nonblocking-constraints.cpp
+++ b/clang/test/Sema/attr-nonblocking-constraints.cpp
@@ -156,6 +156,16 @@ void nb10(
 	static_cast<void (*)()>(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 nb10c(bool x) [[clang::nonblocking]]
+{
+	// Warns that the expression is not nonblocking.
+	return (x ? nb10a : nb10b)();
+}
+
 // Interactions with nonblocking(false)
 void nb11_no_inference_1() [[clang::nonblocking(false)]] // expected-note {{function does not permit inference of 'nonblocking'}}
 {

>From 1dece8572d01d86a8d42c0985ca4058ec4838064 Mon Sep 17 00:00:00 2001
From: Doug Wyatt <dwyatt at apple.com>
Date: Fri, 4 Oct 2024 18:40:01 -0700
Subject: [PATCH 2/3] Fix comment in test.

---
 clang/test/Sema/attr-nonblocking-constraints.cpp | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/clang/test/Sema/attr-nonblocking-constraints.cpp b/clang/test/Sema/attr-nonblocking-constraints.cpp
index ff8caf0e573403..59061dffa372b4 100644
--- a/clang/test/Sema/attr-nonblocking-constraints.cpp
+++ b/clang/test/Sema/attr-nonblocking-constraints.cpp
@@ -162,8 +162,7 @@ int nb10b() [[clang::nonblocking]];
 
 int nb10c(bool x) [[clang::nonblocking]]
 {
-	// Warns that the expression is not nonblocking.
-	return (x ? nb10a : nb10b)();
+	return (x ? nb10a : nb10b)(); // No diagnostic.
 }
 
 // Interactions with nonblocking(false)

>From 30c453ec77dbd3a2b01dae032506e808cf26470c Mon Sep 17 00:00:00 2001
From: Doug Wyatt <dwyatt at apple.com>
Date: Sat, 5 Oct 2024 09:34:27 -0700
Subject: [PATCH 3/3] add another test

---
 clang/test/Sema/attr-nonblocking-constraints.cpp | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/clang/test/Sema/attr-nonblocking-constraints.cpp b/clang/test/Sema/attr-nonblocking-constraints.cpp
index 59061dffa372b4..f23093d4dc8a96 100644
--- a/clang/test/Sema/attr-nonblocking-constraints.cpp
+++ b/clang/test/Sema/attr-nonblocking-constraints.cpp
@@ -159,9 +159,11 @@ void nb10(
 // 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.
 }
 



More information about the cfe-commits mailing list