[clang] [Clang][AST] Fix crash in APValue::LValueBase::getType when we have invalid decl (PR #75130)

Shafik Yaghmour via cfe-commits cfe-commits at lists.llvm.org
Thu Dec 14 11:25:25 PST 2023


https://github.com/shafik updated https://github.com/llvm/llvm-project/pull/75130

>From 8a169838778e333e6bf14a7156a6220d09b5818a Mon Sep 17 00:00:00 2001
From: Shafik Yaghmour <shafik.yaghmour at intel.com>
Date: Mon, 11 Dec 2023 18:35:57 -0800
Subject: [PATCH] [Clang][AST] Fix crash in APValue::LValueBase::getType when
 we have invalid decl

In some cases when calling APValue::LValueBase::getType() when we have a
ValueDecl in some cases we don't handle invalid decls. We iterating over
redeclarations we reset the current decl to the current most recent decl and
we check the next redeclaration to ensure it is not invalid.

Fixes: https://github.com/llvm/llvm-project/issues/69468
---
 clang/docs/ReleaseNotes.rst |  4 ++++
 clang/lib/AST/APValue.cpp   |  4 +++-
 clang/test/AST/gh69468.cpp  | 14 ++++++++++++++
 3 files changed, 21 insertions(+), 1 deletion(-)
 create mode 100644 clang/test/AST/gh69468.cpp

diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index 783dc7333af7e2..988eec5ed6f995 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -641,6 +641,10 @@ Bug Fixes in This Version
   Fixes (`#67317 <https://github.com/llvm/llvm-project/issues/67317>`_)
 - Clang now properly diagnoses use of stand-alone OpenMP directives after a
   label (including ``case`` or ``default`` labels).
+- Fix crash when dealing with ill-formed code where we were not handling invalid
+  redeclarations properly.
+  Fixes (`#69468 <https://github.com/llvm/llvm-project/issues/69468>`_)
+  
 
   Before:
 
diff --git a/clang/lib/AST/APValue.cpp b/clang/lib/AST/APValue.cpp
index 4eae308ef5b34c..2ccd83a1d4823d 100644
--- a/clang/lib/AST/APValue.cpp
+++ b/clang/lib/AST/APValue.cpp
@@ -70,11 +70,13 @@ QualType APValue::LValueBase::getType() const {
     // constexpr int *p = &arr[1]; // valid?
     //
     // For now, we take the most complete type we can find.
-    for (auto *Redecl = cast<ValueDecl>(D->getMostRecentDecl()); Redecl;
+    for (auto *Redecl = cast<ValueDecl>(D->getMostRecentDecl());
+         Redecl && !Redecl->isInvalidDecl();
          Redecl = cast_or_null<ValueDecl>(Redecl->getPreviousDecl())) {
       QualType T = Redecl->getType();
       if (!T->isIncompleteArrayType())
         return T;
+      D = Redecl;
     }
     return D->getType();
   }
diff --git a/clang/test/AST/gh69468.cpp b/clang/test/AST/gh69468.cpp
new file mode 100644
index 00000000000000..8c93fa5e828ac7
--- /dev/null
+++ b/clang/test/AST/gh69468.cpp
@@ -0,0 +1,14 @@
+// RUN: %clang_cc1 -verify %s
+
+
+a[i] = b[i]; // expected-error {{use of undeclared identifier 'i'}} \
+             // expected-error {{a type specifier is required for all declarations}} \
+	     // expected-error {{use of undeclared identifier 'b'}} \
+	     // expected-error {{use of undeclared identifier 'i'}}
+extern char b[];
+extern char a[];
+
+void foo(int j) {
+  // This used to crash here
+  a[j] = b[j];
+}



More information about the cfe-commits mailing list