Testcase: namespace x { extern "C" const int y; }; using x::y; extern "C" int const y=0; ------- The testcase is orginally from Alex Rosenberg on the IRC channel, modified to make it valid code so that the linkage specifications match. This used to work before 4.0.0
Confirmed.
Subject: Bug 27227 Author: mmitchel Date: Wed Jun 14 17:44:36 2006 New Revision: 114647 URL: http://gcc.gnu.org/viewcvs?root=gcc&view=rev&rev=114647 Log: PR c++/27227 * decl.c (decls_match): Allow an extern "C" variable declarations from different namespaces to match. (duplicate_decls): Disallow redeclaring a variable with a different linkage specification. PR c++/27227 * g++.dg/lookup/linkage1.C: New test. * g++.dg/lookup/linkage2.C: Likewise. Added: trunk/gcc/testsuite/g++.dg/lookup/linkage1.C trunk/gcc/testsuite/g++.dg/lookup/linkage2.C Modified: trunk/gcc/cp/ChangeLog trunk/gcc/cp/decl.c trunk/gcc/testsuite/ChangeLog
Fixed in 4.2.0.
Subject: Bug 27227 Author: mmitchel Date: Wed Jun 14 19:17:19 2006 New Revision: 114652 URL: http://gcc.gnu.org/viewcvs?root=gcc&view=rev&rev=114652 Log: PR c++/27227 * decl.c (decls_match): Allow an extern "C" variable declarations from different namespaces to match. (duplicate_decls): Disallow redeclaring a variable with a different linkage specification. PR c++/27227 * g++.dg/lookup/linkage1.C: New test. * g++.dg/lookup/linkage2.C: Likewise. Added: branches/gcc-4_1-branch/gcc/testsuite/g++.dg/lookup/linkage1.C branches/gcc-4_1-branch/gcc/testsuite/g++.dg/lookup/linkage2.C Modified: branches/gcc-4_1-branch/gcc/cp/ChangeLog branches/gcc-4_1-branch/gcc/cp/decl.c branches/gcc-4_1-branch/gcc/testsuite/ChangeLog
Fixedin 4.1.2.
Could I get clarification if the following error is a desired effect of this change. Prior to this, the included program gave no error. I believe the change was caused by this patch. This is causing a problem with the HP-UX definition of errno, but it we want this error, I can fixheaders the header file in question. e.c:1: error: previous declaration of 'int i' with 'C++' linkage e.c:4: error: conflicts with new declaration with 'C' linkage [hpclear8] $ cat e.c extern int i; extern "C" { extern int i; }
(In reply to comment #6) > e.c:1: error: previous declaration of 'int i' with 'C++' linkage > e.c:4: error: conflicts with new declaration with 'C' linkage > > extern int i; > extern "C" { > extern int i; > } Not this is a confirmation that the above is invalid code but EDG also errors out.
The standard says in 7.5/5: "If two declarations of the same function or object specify different linkage-specifications [...] the program is ill-formed if the declarations appear in the same translation unit [...]". That is why code like that in comment 6 is now rejected.
(In reply to comment #6) > Could I get clarification if the following error is a desired effect of this > change. Prior to this, the included program gave no error. I believe the > change was caused by this patch. > > e.c:1: error: previous declaration of 'int i' with 'C++' linkage > e.c:4: error: conflicts with new declaration with 'C' linkage > > [hpclear8] $ cat e.c > > extern int i; > > extern "C" { > extern int i; > } So apparently this is invalid code. However, I feel very strongly that a point release of GCC should *not* introduce a new error - Mark, please modify the patch applied to the 4.1 branch in a way to allow this code.
(In reply to comment #9) > So apparently this is invalid code. However, I feel very strongly that a point > release of GCC should *not* introduce a new error - Mark, please modify the > patch applied to the 4.1 branch in a way to allow this code. Why? It is better to reject invalid code even than keeping backwards compatiblity.
Hmm, actually the defect report about the code in comment #6 is still active so I agree that we should not reject it on the release branch. http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_active.html#563
(In reply to comment #10) > Why? It is better to reject invalid code even than keeping backwards > compatiblity. No, it's not - not in a minor point release. Users expect that a minor point release is backwards compatible. Upgrading from 4.1.1 to 4.1.2 should be painless, i.e. fix bugs only. But now we suddenly have 13 package build failures in Debian.
(In reply to comment #12) > Upgrading from 4.1.1 to 4.1.2 should be painless, i.e. fix bugs only. But now > we suddenly have 13 package build failures in Debian. It is a bug fix, just not what normal people think about bug fix. If there was not a defect report still open about this case, I actually would say this was a bug fix but this one is a bit weird as the defect report was not resolved yet. I have a feeling Mark should not have changed the behavior until it was resolved as there was no comments on the defect report either. Anyways I filed PR 28389 about the defect report so that people know that the standard is ambiguous and that maybe we can get the behavior back to the orginal
(In reply to comment #13) > > Upgrading from 4.1.1 to 4.1.2 should be painless, i.e. fix bugs only. But now > > we suddenly have 13 package build failures in Debian. > It is a bug fix, just not what normal people think about bug fix. That's right. Not what normal people, i.e. users of GCC, see as a bug fix. If code is invalid but it works, please leave it alone in a stable point release.
Subject: Re: [4.0 Regression] rejects valid code with some extern "C" tbm at cyrius dot com wrote: > So apparently this is invalid code. However, I feel very strongly that a point > release of GCC should *not* introduce a new error - Mark, please modify the > patch applied to the 4.1 branch in a way to allow this code. As a matter of policy, we don't intentionally introduce errors on release branches. However, it is far too strong a statement to say that we should never introduce an error. In many such cases, the new error is either indicative of a situation in which the compiler was behaving randomly (i.e., in which the generated code made no sense) or the new error is a side-effect of some other important change. In this case, we were rejecting valid code. We no longer reject valid code; instead we reject invalid code. (Andrew's comment about the DR being open is accurate, but the DR will almost certainly be resolved so as to make this code invalid.) If you want to find a way to accept the invalid code on the release branch, that's your privilege. I consider it a better use of my (very limited) time to fix places where the compiler fails to conform to the standard.
Fixed in GCC-4.1.2