https://github.com/dmaclach created 
https://github.com/llvm/llvm-project/pull/220401

When visiting an ObjCInterfaceTypeLoc, check if the spelled name matches a 
@compatibility_alias. If so, report the alias declaration instead of the 
underlying interface declaration. This ensures that include-cleaner attributes 
the usage to the header defining the alias.

>From a32a74db95d194f0774b13cf15edd07b0482264e Mon Sep 17 00:00:00 2001
From: Dave MacLachlan <[email protected]>
Date: Tue, 1 Sep 2026 14:51:07 -0700
Subject: [PATCH] [include-cleaner] Support ObjC @compatibility_alias in
 WalkAST.

When visiting an ObjCInterfaceTypeLoc, check if the spelled name matches a 
@compatibility_alias. If so, report the alias declaration instead of the 
underlying interface declaration. This ensures that include-cleaner attributes 
the usage to the header defining the alias.
---
 .../include-cleaner/lib/WalkAST.cpp           | 22 ++++++++++++++++++-
 .../include-cleaner/unittests/WalkASTTest.cpp |  4 ++--
 2 files changed, 23 insertions(+), 3 deletions(-)

diff --git a/clang-tools-extra/include-cleaner/lib/WalkAST.cpp 
b/clang-tools-extra/include-cleaner/lib/WalkAST.cpp
index 13978b0462acd..0f02ed3de76d8 100644
--- a/clang-tools-extra/include-cleaner/lib/WalkAST.cpp
+++ b/clang-tools-extra/include-cleaner/lib/WalkAST.cpp
@@ -441,7 +441,27 @@ class ASTWalker : public RecursiveASTVisitor<ASTWalker> {
   // Objective-C support
 
   bool VisitObjCInterfaceTypeLoc(ObjCInterfaceTypeLoc TL) {
-    reportType(TL.getNameLoc(), TL.getIFaceDecl());
+    ObjCInterfaceDecl *IFace = TL.getIFaceDecl();
+    if (!IFace)
+      return true;
+
+    SourceLocation Loc = TL.getNameLoc();
+    ASTContext &Ctx = IFace->getASTContext();
+    StringRef SpelledName =
+        Lexer::getSourceText(CharSourceRange::getTokenRange(Loc),
+                             Ctx.getSourceManager(), Ctx.getLangOpts());
+    if (!SpelledName.empty() && SpelledName != IFace->getName()) {
+      // We may have a @compatibility_alias.
+      for (auto *D : Ctx.getTranslationUnitDecl()->decls()) {
+        if (auto *Alias = dyn_cast<ObjCCompatibleAliasDecl>(D)) {
+          if (Alias->getName() == SpelledName) {
+            report(Loc, Alias);
+            return true;
+          }
+        }
+      }
+    }
+    reportType(Loc, IFace);
     return true;
   }
 
diff --git a/clang-tools-extra/include-cleaner/unittests/WalkASTTest.cpp 
b/clang-tools-extra/include-cleaner/unittests/WalkASTTest.cpp
index 1e2ff594ef87a..3c82fd447ab99 100644
--- a/clang-tools-extra/include-cleaner/unittests/WalkASTTest.cpp
+++ b/clang-tools-extra/include-cleaner/unittests/WalkASTTest.cpp
@@ -1120,9 +1120,9 @@ TEST(WalkAST, ObjCCompatibleAliasDecl) {
 
 TEST(WalkAST, ObjCCompatibleAliasUsage) {
   testWalk(R"objc(
-    @interface $explicit^MyClass
+    @interface MyClass
     @end
-    @compatibility_alias AliasName MyClass;
+    $explicit^@compatibility_alias AliasName MyClass;
   )objc",
            R"objc(
     void test() {

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

Reply via email to