================
@@ -559,21 +595,56 @@ void UseAfterMoveCheck::check(const 
MatchFinder::MatchResult &Result) {
                               ContainingCtorInit->IgnoreImplicit())
           BeforeMove = false;
         if (!BeforeMove)
-          CodeBlocks.push_back(Init->getInit());
+          CodeBlocks.push_back({ContainingCtor, Init->getInit()});
       }
     }
   } else if (ContainingLambda) {
-    CodeBlocks.push_back(ContainingLambda->getBody());
+    CodeBlocks.push_back(
+        {ContainingLambda->getCallOperator(), ContainingLambda->getBody()});
   } else if (ContainingFunc) {
-    CodeBlocks.push_back(ContainingFunc->getBody());
+    CodeBlocks.push_back({ContainingFunc, ContainingFunc->getBody()});
   }
 
-  for (Stmt *CodeBlock : CodeBlocks) {
+  for (auto [ContainingDecl, CodeBlock] : CodeBlocks) {
     UseAfterMoveFinder Finder(Result.Context, InvalidationFunctions,
                               ReinitializationFunctions);
-    if (auto Use = Finder.find(CodeBlock, MovingCall, Arg))
-      emitDiagnostic(MovingCall, Arg, *Use, this, Result.Context,
-                     determineMoveType(MoveDecl));
+    if (Arg) {
+      // Non-coroutine cases
+      if (auto Use = Finder.find(CodeBlock, MovingCall, Arg))
+        emitDiagnostic(MovingCall, Arg, *Use, this, Result.Context,
+                       determineMoveType(MoveDecl));
+    } else {
+      // Coroutine cases (use-after-suspend, to catch pointers to 
thread-locals)
+      llvm::SmallVector<const DeclRefExpr *> DeclRefs;
+      // Find all local variables declared inside this code block
+      auto InterestingCallMatcher = callExpr(
+          callee(
+              
functionDecl(matchers::matchesAnyListedRegexName(NonlocalAccessors))),
+          unless(hasParent(memberExpr(
+              hasDeclaration(functionDecl(unless(returns(hasCanonicalType(
+                  anyOf(referenceType(), pointerType()))))))))));
+      auto DeclsMatcher =
+          declRefExpr(to(varDecl(unless(isImplicit()),
+                                 hasDeclContext(equalsNode(ContainingDecl)),
+                                 hasType(hasUnqualifiedDesugaredType(
+                                     anyOf(pointerType(), referenceType()))),
+                                 hasInitializer(anyOf(
+                                     InterestingCallMatcher,
+                                     hasDescendant(InterestingCallMatcher))))))
+              .bind("declref");
+      for (const auto &Bound :
+           match(findAll(DeclsMatcher), *CodeBlock, *Result.Context)) {
+        DeclRefs.push_back(Bound.getNodeAs<DeclRefExpr>("declref"));
+      }
+      for (const DeclRefExpr *DeclRef : DeclRefs) {
+        if (auto Use = Finder.find(CodeBlock, MovingCall, DeclRef)) {
+          emitDiagnostic(MovingCall, DeclRef, *Use, this, Result.Context,
+                         isa<CoroutineSuspendExpr>(MovingCall)
----------------
zwuis wrote:

Can we use `assert` instead?

https://github.com/llvm/llvm-project/pull/172566
_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to