-
Notifications
You must be signed in to change notification settings - Fork 15.1k
[Clang] FunctionEffects: properly extract the type of a bound member member function from a CallExpr. #166101
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
…member function from a CallExpr.
|
@llvm/pr-subscribers-clang Author: Doug Wyatt (dougsonos) ChangesThere's a bug illustrated by this example: In both cases we have a Full diff: https://github.com/llvm/llvm-project/pull/166101.diff 2 Files Affected:
diff --git a/clang/lib/Sema/SemaFunctionEffects.cpp b/clang/lib/Sema/SemaFunctionEffects.cpp
index 8590ee831084f..6d7bcbf53fe0f 100644
--- a/clang/lib/Sema/SemaFunctionEffects.cpp
+++ b/clang/lib/Sema/SemaFunctionEffects.cpp
@@ -1208,8 +1208,17 @@ class Analyzer {
return true;
}
- // No Decl, just an Expr. Just check based on its type.
- checkIndirectCall(Call, CalleeExpr->getType());
+ // No Decl, just an Expr. Just check based on its type. Bound member
+ // functions are a special expression type and need to be specially
+ // unpacked.
+ QualType CalleeExprQT = CalleeExpr->getType();
+ if (CalleeExpr->isBoundMemberFunction(Outer.S.getASTContext())) {
+ QualType QT = Expr::findBoundMemberType(CalleeExpr);
+ if (!QT.isNull()) {
+ CalleeExprQT = QT;
+ }
+ }
+ checkIndirectCall(Call, CalleeExprQT);
return true;
}
diff --git a/clang/test/Sema/attr-nonblocking-constraints.cpp b/clang/test/Sema/attr-nonblocking-constraints.cpp
index b26a945843696..22f7e23f81cf9 100644
--- a/clang/test/Sema/attr-nonblocking-constraints.cpp
+++ b/clang/test/Sema/attr-nonblocking-constraints.cpp
@@ -236,9 +236,22 @@ void nb13() [[clang::nonblocking]] { nb12(); }
struct PTMFTester {
typedef void (PTMFTester::*ConvertFunction)() [[clang::nonblocking]];
+ ConvertFunction mConvertFunc;
+
void convert() [[clang::nonblocking]];
- ConvertFunction mConvertFunc;
+ template <typename T>
+ struct Holder {
+ T value;
+
+ T& operator*() { return value; }
+ };
+
+
+ void ptmfInExpr(Holder<ConvertFunction>& holder) [[clang::nonblocking]]
+ {
+ (this->*(*holder))(); // This should not generate a warning.
+ }
};
void PTMFTester::convert() [[clang::nonblocking]]
|
Sirraide
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Some minor comments; lgtm otherwise
|
|
||
| void ptmfInExpr(Holder<ConvertFunction>& holder) [[clang::nonblocking]] | ||
| { | ||
| (this->*(*holder))(); // This should not generate a warning. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can you also add
((*this).*(*holder))();as well as a test case that shows that we do issue a warning if the member function is not nonblocking.
Co-authored-by: Sirraide <aeternalmail@gmail.com>
…w/nb-ptmf-in-expr
There's a bug illustrated by this example:
In both cases we have a
CXXMemberCallExpr. Insucceeds, the expression refers to aDecl(func) and gets a useful PTMF type. Infails, the expression does not refer to aDecland its type is special, printed asbound member function.Exprprovides a method for extracting the true type so we can use that in this situation.