Pourquoi les mêmes variables locales externes nommées dans différents blocs obtiennent des liens différents entre les compilateurs en c ++?


12

Pendant que je vérifiais simplement quels liens sont accordés aux variables locales externes,
j'ai constaté que certains comportements différents entre les compilateurs

par exemple, si j'ai testé le code ci-dessous
comme vous le voyez dans les commentaires, les variables varont des liens différents

// foo.cpp
int var = 10;                // external linkage

// main.cpp
#include <iostream>

static int var = 100;        // internal linkage

int main() {
    extern int var;          // internal linkage
    std::cout << var << std::endl;
    {
        extern int var;      // g++: external linkage , clang++: internal linkage
        std::cout << var << std::endl;
        {
            extern int var;  // g++: external linkage , clang++: internal linkage
            std::cout << var << std::endl;
        }
    }
}       

le résultat est

  • g ++: "100 10 10"
  • clang ++: "100 100 100" (msvc ++)

Je peux voir d'après le résultat que s'il y a plus de deux blocs imbriqués,
g ++ accorde simplement des liens externes aux variables

J'ai pu trouver une phrase connexe dans la norme
mais elle n'est toujours pas claire car son comportement est différent selon les compilateurs
( https://eel.is/c++draft/basic.link#6 )

J'ai peur que mon anglais soit mauvais, donc je ne peux pas le comprendre correctement.
Si quelqu'un a une idée de quels compilateurs sont bien conformes à la norme
et si possible quelqu'un pourrait-il élaborer ce que la norme dit exactement pour moi?


1
Related stackoverflow.com/questions/41978949/… Je crois que c'est un bogue gcc, la norme donne l'exemple avec f()fonction et le plus extern void f()interne a une liaison interne - vardevrait également avoir une liaison interne, car elle fait référence à la même "entité".
KamilCuk

Les déclarations de portée de bloc de l'OMI d'entités avec une liaison externe sont mauvaises et le langage serait préférable de les interdire
MM

@MM: les unités de module le font!
Davis Herring

Réponses:


4

C'est le sujet du numéro ouvert CWG1839 . L' intention actuelle est que le comportement de Clang et MSVC soit correct.

En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.