[llvm-branch-commits] [clang] 9486367 - Revert "[Clang] Diagnose UB and emit error when identifier has both internal …"
via llvm-branch-commits
llvm-branch-commits at lists.llvm.org
Wed Apr 22 03:45:58 PDT 2026
Author: Aaron Ballman
Date: 2026-04-22T06:45:54-04:00
New Revision: 9486367e5bc04dedb7a40432bf6c8676963c1822
URL: https://github.com/llvm/llvm-project/commit/9486367e5bc04dedb7a40432bf6c8676963c1822
DIFF: https://github.com/llvm/llvm-project/commit/9486367e5bc04dedb7a40432bf6c8676963c1822.diff
LOG: Revert "[Clang] Diagnose UB and emit error when identifier has both internal …"
This reverts commit 1e2175ec4df79de3c18c504dea0dcbaab4b38306.
Added:
Modified:
clang/docs/ReleaseNotes.rst
clang/include/clang/Basic/DiagnosticSemaKinds.td
clang/lib/Sema/SemaDecl.cpp
clang/test/C/C2y/n3410.c
clang/www/c_status.html
Removed:
clang/test/Sema/linkage-internal-extern.c
clang/test/Sema/linkage-internal-extern.cpp
################################################################################
diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index b25bc08b033d2..174731ca0a6ff 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -155,12 +155,6 @@ C Language Changes
C2y Feature Support
^^^^^^^^^^^^^^^^^^^
-- Clang now diagnoses the use of the same identifier with both internal and
- external linkage within a translation unit, as made ill-formed by
- `N3410 <https://www.open-std.org/jtc1/sc22/wg14/www/docs/n3410.pdf>`_.
- This is also diagnosed in older C language modes as the behavior was
- undefined prior to C2y. (#GH54215)
-
C23 Feature Support
^^^^^^^^^^^^^^^^^^^
- Clang now allows C23 ``constexpr`` struct member access through the dot operator in constant expressions. (#GH178349)
diff --git a/clang/include/clang/Basic/DiagnosticSemaKinds.td b/clang/include/clang/Basic/DiagnosticSemaKinds.td
index 3ab8dd412a7ad..dc86a0b58d8f9 100644
--- a/clang/include/clang/Basic/DiagnosticSemaKinds.td
+++ b/clang/include/clang/Basic/DiagnosticSemaKinds.td
@@ -6534,9 +6534,6 @@ def err_inline_declaration_block_scope : Error<
"inline declaration of %0 not allowed in block scope">;
def err_static_non_static : Error<
"static declaration of %0 follows non-static declaration">;
-def err_internal_extern_mismatch : Error<
- "variable %0 declared with both internal and external linkage "
- "in the same translation unit%select{; behavior is undefined|}1">;
def err_
diff erent_language_linkage : Error<
"declaration of %0 has a
diff erent language linkage">;
def ext_retained_language_linkage : Extension<
diff --git a/clang/lib/Sema/SemaDecl.cpp b/clang/lib/Sema/SemaDecl.cpp
index 83f536cef913d..6afdd73328eba 100644
--- a/clang/lib/Sema/SemaDecl.cpp
+++ b/clang/lib/Sema/SemaDecl.cpp
@@ -4802,25 +4802,6 @@ void Sema::MergeVarDecl(VarDecl *New, LookupResult &Previous) {
return New->setInvalidDecl();
}
}
-
- // C2y 6.7.1p7:
- // Within a translation unit, the same identifier shall not appear with
- // both internal and external linkage.
- //
- // In C11 through C23, this was undefined behavior (C11 6.2.2p7).
- //
- // This can occur when an extern declaration in block scope finds a file-scope
- // static declaration, but a no-linkage local variable shadowed the static,
- // preventing linkage inheritance per C2y 6.2.2p4.
- if (!getLangOpts().CPlusPlus && New->isLocalVarDecl() &&
- New->hasExternalStorage() && Old->isFileVarDecl() && Old->hasLinkage() &&
- Previous.isShadowed() && Old->getFormalLinkage() == Linkage::Internal) {
- Diag(New->getLocation(), diag::err_internal_extern_mismatch)
- << New->getDeclName() << getLangOpts().C2y;
- Diag(OldLocation, PrevDiag);
- return New->setInvalidDecl();
- }
-
// C99 6.2.2p4:
// For an identifier declared with the storage-class specifier
// extern in a scope in which a prior declaration of that
diff --git a/clang/test/C/C2y/n3410.c b/clang/test/C/C2y/n3410.c
index 7ce3c2916d300..e1cb41f375b82 100644
--- a/clang/test/C/C2y/n3410.c
+++ b/clang/test/C/C2y/n3410.c
@@ -1,6 +1,6 @@
// RUN: %clang_cc1 -verify -std=c2y -Wall -pedantic -Wno-unused %s
-/* WG14 N3410: Clang 23
+/* WG14 N3410: No
* Slay Some Earthly Demons XI
*
* It is now ill-formed for the same identifier within a TU to have both
@@ -24,17 +24,19 @@ void func2() {
extern int b; // Ok
}
-static int c, d; // expected-note 2 {{previous definition is here}}
+static int c, d;
void func3() {
int c; // no linkage,
diff erent object from the one declared above.
for (int d;;) {
// This 'c' is the same as the one declared at file scope, but because of
// the local scope 'c', the file scope 'c' is not visible.
- extern int c; // expected-error {{declared with both internal and external linkage}}
+ // FIXME: This should be diagnosed under N3410.
+ extern int c;
// This 'd' is the same as the one declared at file scope as well, but
// because of the 'd' declared within the for loop, the file scope 'd' is
// also not visible, same as with 'c'.
- extern int d; // expected-error {{declared with both internal and external linkage}}
+ // FIXME: This should be diagnosed under N3410.
+ extern int d;
}
for (static int e;;) {
extern int e; // Ok for the same reason as 'b' above.
diff --git a/clang/test/Sema/linkage-internal-extern.c b/clang/test/Sema/linkage-internal-extern.c
deleted file mode 100644
index 42591c5b21f0b..0000000000000
--- a/clang/test/Sema/linkage-internal-extern.c
+++ /dev/null
@@ -1,36 +0,0 @@
-// RUN: %clang_cc1 -verify -fsyntax-only %s
-
-// C11 6.2.2p7: same identifier with both internal and external linkage is UB.
-
-// Conflicting linkage (UB)
-
-static int x; // expected-note {{previous}}
-void test_basic_shadow(void) {
- int x;
- { extern int x; } // expected-error {{declared with both internal and external linkage}}
-}
-
-static int y; // expected-note {{previous}}
-void test_deep_nesting(void) {
- int y;
- { int y; { { extern int y; } } } // expected-error {{declared with both internal and external linkage}}
-}
-
-static int p; // expected-note {{previous}}
-void test_param_shadow(int p) {
- { extern int p; } // expected-error {{declared with both internal and external linkage}}
-}
-
-// Valid cases
-
-static int a;
-void test_no_shadow(void) {
- extern int a;
-}
-
-void test_no_file_scope(void) {
- for (static int b = 0;;) {
- extern int b;
- break;
- }
-}
diff --git a/clang/test/Sema/linkage-internal-extern.cpp b/clang/test/Sema/linkage-internal-extern.cpp
deleted file mode 100644
index ab084767305fd..0000000000000
--- a/clang/test/Sema/linkage-internal-extern.cpp
+++ /dev/null
@@ -1,19 +0,0 @@
-// RUN: %clang_cc1 -verify -fsyntax-only -std=c++17 %s
-
-// expected-no-diagnostics
-
-// CWG 426 / [basic.link]p6: the same identifier with both internal and
-// external linkage should be ill-formed in C++, but Clang does not yet
-// diagnose this due to ABI break concerns. This test documents current
-// behavior.
-
-static int x;
-void test_shadow(void) {
- int x;
- {
- // FIXME: Per CWG 426, this should be ill-formed because the
- // file-scope 'x' has internal linkage but this 'extern' gets
- // external linkage due to the local shadow.
- extern int x;
- }
-}
diff --git a/clang/www/c_status.html b/clang/www/c_status.html
index 4b3695831de58..5270033471167 100644
--- a/clang/www/c_status.html
+++ b/clang/www/c_status.html
@@ -283,7 +283,7 @@ <h2 id="c2y">C2y implementation status</h2>
<tr>
<td>Slay Some Earthly Demons XI</td>
<td><a href="https://www.open-std.org/jtc1/sc22/wg14/www/docs/n3410.pdf">N3410</a></td>
- <td class="unreleased" align="center">Clang 23</td>
+ <td class="none" align="center">No</td>
</tr>
<tr>
<td>Slay Some Earthly Demons XII</td>
More information about the llvm-branch-commits
mailing list