| Register | FAQ | Calendar | Search | Today's Posts | Mark Forums Read |
|
#1
| |||
| |||
| Hi everyone, AFAIK external linkage allows you to refer to variables/functions outside of the current translation unit. A variable in an unnamed namespace is similar to declaring a static variable, but according to the standard there is a difference: "While this is essentially true in practical effect, there are subtle differences. Using static as shown here causes "i" to have internal linkage. When declared in an unnamed namespace without the use of static, it has external linkage. This use of static is officially deprecated (C++ Standard 7.3.1.1/2)." To me this means that the variable is accessible outside of the translation unit. However, Herb Schildt's book shows the following: ------------------------------------------------------------------------------------------ While the use of static global declarations is still allowed in C++, a better way to accomplish the same effect is to use an unnamed namespace. For example: File One namespace { int k; } void f1() { k = 99; // OK } File Two extern int k; void f2() { k = 10; // error } Here, k is also restricted to File One. The use of the unnamed namespace rather than static is recommended for new code. ------------------------------------------------------------------------------------------ So how is it that 'k' has external linkage? Thanks Taras |
|
#2
| |||
| |||
| Taras_96 wrote: > AFAIK external linkage allows you to refer to variables/functions > outside of the current translation unit. A variable in an unnamed > namespace is similar to declaring a static variable, but according to > the standard there is a difference: > > > "While this is essentially true in practical effect, there are subtle > differences. Using static as shown here causes "i" to have internal > linkage. When declared in an unnamed namespace without the use of > static, it has external linkage. This use of static is officially > deprecated (C++ Standard 7.3.1.1/2)." > > To me this means that the variable is accessible outside of the > translation unit. There is no way for the compiler to figure out the right name for the variable when compiler *another* translation unit. That's the trick to make it "not available". The name is made up unique while the compiler is compiling that particular translation unit. > However, Herb Schildt's book shows the following: Ugh! Yuck! I'm telling Mom! ...Mom, Taras said the "S" name, and he is reading THAT book!... Throw that book away, Taras, and get yourself a *real* C++ book. Visit www.accu.org, the book review section, to see what are the recommended titles. > [..] > > So how is it that 'k' has external linkage? It just does. The compiler provides it with external linkage. What is the difference how it accomplishes that? V -- Please remove capital 'A's when replying by e-mail I do not respond to top-posted replies, please don't ask |
|
#3
| |||
| |||
| On Sep 6, 8:56 pm, Taras_96 <taras...@gmail.com> wrote: > AFAIK external linkage allows you to refer to > variables/functions outside of the current translation unit. A > variable in an unnamed namespace is similar to declaring a > static variable, but according to the standard there is a > difference: > "While this is essentially true in practical effect, there are > subtle differences. Using static as shown here causes "i" to > have internal linkage. When declared in an unnamed namespace > without the use of static, it has external linkage. This use > of static is officially deprecated (C++ Standard 7.3.1.1/2)." > To me this means that the variable is accessible outside of > the translation unit. However, Herb Schildt's book shows the > following: > ------------------------------------------------------------------------------------------ > While the use of static global declarations is still allowed > in C++, a better way to accomplish the same effect is to use > an unnamed namespace. For example: > File One > namespace { > int k;} > void f1() { > k = 99; // OK > } > File Two > extern int k; > void f2() { > k = 10; // error} > Here, k is also restricted to File One. The use of the unnamed > namespace rather than static is recommended for new code. > ------------------------------------------------------------------------------------------ > So how is it that 'k' has external linkage? It has external linkage, just like any other variable. In file one, the definition is in a namespace with a name unique to the file; in file 2, k is in global namespace. This is more or less the same as if you had: File One: namespace TopSecrectName { int k ; } using TopSecrectName ; // ... File Two extern int k ; // ... Since the two k aren't in the same namespace, their qualified names are different, and they can only be different entities. -- James Kanze (GABI Software) email:james.kanze@gmail.com Conseils en informatique orientée objet/ Beratung in objektorientierter Datenverarbeitung 9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34 |
|
#4
| |||
| |||
| In article <0c975cd6-22fb-4824-a4c7-4d5b58e493cd@j22g2000hsf.googlegroups.com>, Taras_96 <taras.di@gmail.com> wrote: > AFAIK external linkage allows you to refer to variables/functions > outside of the current translation unit. A variable in an unnamed > namespace is similar to declaring a static variable, but according to > the standard there is a difference: > > "While this is essentially true in practical effect, there are subtle > differences. Using static as shown here causes "i" to have internal > linkage. When declared in an unnamed namespace without the use of > static, it has external linkage. This use of static is officially > deprecated (C++ Standard 7.3.1.1/2)." > > To me this means that the variable is accessible outside of the > translation unit. [...] External linkage has other useful consequences as well. The first that comes to mind is that the unnamed namespace allows templates that are "local" to a translation unit. They must have external linkage, and the unnamed namespace is the only way to provide that WITHOUT making them accessible outside the translation unit, since they cannot be static. |
|
#5
| |||
| |||
| On Sep 7, 3:28 am, blargg....@gishpuppy.com (blargg) wrote: > In article > <0c975cd6-22fb-4824-a4c7-4d5b58e49...@j22g2000hsf.googlegroups.com>, > Taras_96 <taras...@gmail.com> wrote: > > AFAIK external linkage allows you to refer to > > variables/functions outside of the current translation unit. > > A variable in an unnamed namespace is similar to declaring a > > static variable, but according to the standard there is a > > difference: > > "While this is essentially true in practical effect, there > > are subtle differences. Using static as shown here causes > > "i" to have internal linkage. When declared in an unnamed > > namespace without the use of static, it has external > > linkage. This use of static is officially deprecated (C++ > > Standard 7.3.1.1/2)." > > To me this means that the variable is accessible outside of > > the translation unit. [...] > External linkage has other useful consequences as well. The > first that comes to mind is that the unnamed namespace allows > templates that are "local" to a translation unit. They must > have external linkage, and the unnamed namespace is the only > way to provide that WITHOUT making them accessible outside the > translation unit, since they cannot be static. Not just templates, everything but references, variables and functions. It's the only way to define a local, helper class without risk of name conflict. -- James Kanze (GABI Software) email:james.kanze@gmail.com Conseils en informatique orientée objet/ Beratung in objektorientierter Datenverarbeitung 9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34 |
|
#6
| |||
| |||
| On Sep 6, 8:53*pm, James Kanze <james.ka...@gmail.com> wrote: > On Sep 6, 8:56 pm, Taras_96 <taras...@gmail.com> wrote: > > > > > AFAIK external linkage allows you to refer to > > variables/functions outside of the current translation unit. A > > variable in an unnamed namespace is similar to declaring a > > static variable, but according to the standard there is a > > difference: > > "While this is essentially true in practical effect, there are > > subtle differences. *Using static as shown here causes "i" to > > have internal linkage. *When declared in an unnamed namespace > > without the use of static, it has external linkage. *This use > > of static is officially deprecated (C++ Standard 7.3.1.1/2)." > > To me this means that the variable is accessible outside of > > the translation unit. However, Herb Schildt's book shows the > > following: > > ------------------------------------------------------------------------------------------ > > While the use of static global declarations is still allowed > > in C++, a better way to accomplish the same effect is to use > > an unnamed namespace. For example: > > File One > > namespace { > > int k;} > > void f1() { > > k = 99; // OK > > } > > File Two > > extern int k; > > void f2() { > > k = 10; // error} > > Here, k is also restricted to File One. The use of the unnamed > > namespace rather than static is recommended for new code. > > ------------------------------------------------------------------------------------------ > > So how is it that 'k' has external linkage? > > It has external linkage, just like any other variable. *In file > one, the definition is in a namespace with a name unique to the > file; in file 2, k is in global namespace. *This is more or less Sorry, I don't think I made myself clear enough :*). I meant 'k' in file 1 (ie: how is it that the 'k' in file 1 has external linkage?). > the same as if you had: > > File One: > * * namespace TopSecrectName { > * * int k ; > * * } > * * using TopSecrectName ; > * * // *... > > File Two > * * extern int k ; > * * // *... > > Since the two k aren't in the same namespace, their qualified > names are different, and they can only be different entities. This I understand . I might be getting confused over the meaning of'external linkage'. To me the defining characteristic is that during the linking stage, the linker can 'link in' that variable. So you could have: file 1: int h = 1; file 2; extern int h; // <- this refers to the k defined in file 1 [Side note.. does the 'k' variable in the 'TopSecretName' namespace have internal linkage only?] So, if in fact my interpretation of 'external linkage' is correct, and (in my original example) the 'k' variable in the anonymous namespace does have external linkage, then how can we get file 2 to refer to the k variable in file 1? Thanks Taras |
|
#7
| |||
| |||
| On Sep 6, 8:18*pm, "Victor Bazarov" <v.Abaza...@comAcast.net> wrote: > Taras_96 wrote: > > AFAIK external linkage allows you to refer to variables/functions ...... > There is no way for the compiler to figure out the right name for the > variable when compiler *another* translation unit. *That's the trick > to make it "not available". *The name is made up unique while the > compiler is compiling that particular translation unit. I don't quite understand.. perhaps there's a typo? > > > However, Herb Schildt's book shows the following: > > Ugh! *Yuck! *I'm telling Mom! *...Mom, Taras said the "S" name, and > he is reading THAT book!... - point taken. Does it help that I'm reading it in conjunction withBjarne Stroustrup's book? > > Throw that book away, Taras, and get yourself a *real* C++ book. > Visitwww.accu.org, the book review section, to see what are the > recommended titles. > |
|
#8
| |||
| |||
| On Sep 9, 10:44 am, Taras_96 <taras...@gmail.com> wrote: > On Sep 6, 8:53 pm, James Kanze <james.ka...@gmail.com> wrote: > > the same as if you had: > > File One: > > namespace TopSecrectName { > > int k ; > > } > > using TopSecrectName ; > > // ... > > File Two > > extern int k ; > > // ... > > Since the two k aren't in the same namespace, their qualified > > names are different, and they can only be different entities. > This I understand . I might be getting confused over the> meaning of 'external linkage'. To me the defining > characteristic is that during the linking stage, the linker > can 'link in' that variable. That's sort of it. Formally, it means that the fully qualified name refers to the same entity in different translation units. In this case, any reference to ::TopSecrectName::k in any translation unit would refer to the same entity, the variable k defined in File One. As a programmer, of course, there's no possible way you could refer to ::TopSecrectName::k, because there's no way you can know what TopSecrectName really is. For the compiler, this isn't necessarily true; the compiler can "leak" the TopSecrectName somehow, and may actually do so in some strategies of template instantiation (particularly if export is involved). But that's an implementation detail you're not supposed to see:-). > So you could have: > file 1: > int h = 1; > file 2; > extern int h; // <- this refers to the k defined in file 1 > [Side note.. does the 'k' variable in the 'TopSecretName' > namespace have internal linkage only?] No. It's just like any other variable. The only thing is that the compiler generates a special name for the namespace, unique to the translation unit. > So, if in fact my interpretation of 'external linkage' is > correct, and (in my original example) the 'k' variable in the > anonymous namespace does have external linkage, then how can > we get file 2 to refer to the k variable in file 1? You can't, because you can't name the namespace its in. In practice, you might be able to by looking at the mangled generated name, demangling it to determine what the TopSecretName actually was, and declaring a namespace with that name. However, the compiler might use characters in that name that you're not allowed to use in a name in C++ (g++ uses a . in the name, for example), and its very likely that the compiler generates a different name each time it recompiles the source (true with both Sun CC and g++). -- James Kanze (GABI Software) email:james.kanze@gmail.com Conseils en informatique orientée objet/ Beratung in objektorientierter Datenverarbeitung 9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34 |
|
#9
| |||
| |||
| On Sep 9, 10:40*am, James Kanze <james.ka...@gmail.com> wrote: > On Sep 9, 10:44 am, Taras_96 <taras...@gmail.com> wrote: > > > No. *It's just like any other variable. *The only thing is that > the compiler generates a special name for the namespace, unique > to the translation unit. > > > So, if in fact my interpretation of 'external linkage' is > > correct, and (in my original example) the 'k' variable in the > > anonymous namespace does have external linkage, then how can > > we get file 2 to refer to the k variable in file 1? > > You can't, because you can't name the namespace its in. > > In practice, you might be able to by looking at the mangled > generated name, demangling it to determine what the > TopSecretName actually was, and declaring a namespace with that > name. *However, the compiler might use characters in that name > that you're not allowed to use in a name in C++ (g++ uses a . in > the name, for example), and its very likely that the compiler > generates a different name each time it recompiles the source > (true with both Sun CC and g++). > I think I understand now. In rough terms, the compiler generates a name for each namespace that the linker can then use to link up matching namespaces. In the anonymous namespace case, the compiler still generates that name (and thus it has external linkage), but because that name is not visible to the user (and the generation of that name is implementation specific), then in practice you can't really refer to the anonyous namespace. If you had the access to the generated name and the algorithm that generates it, you could do something like this (in pseudo-code terms): using inverse_generate_name(generated_anonymous_name_fro m file 1) Sound about right ?Taras |
|
#10
| |||
| |||
| On Sep 9, 10:40*am, James Kanze <james.ka...@gmail.com> wrote: > On Sep 9, 10:44 am, Taras_96 <taras...@gmail.com> wrote: > > > No. *It's just like any other variable. *The only thing is that > the compiler generates a special name for the namespace, unique > to the translation unit. > > > So, if in fact my interpretation of 'external linkage' is > > correct, and (in my original example) the 'k' variable in the > > anonymous namespace does have external linkage, then how can > > we get file 2 to refer to the k variable in file 1? > > You can't, because you can't name the namespace its in. > > In practice, you might be able to by looking at the mangled > generated name, demangling it to determine what the > TopSecretName actually was, and declaring a namespace with that > name. *However, the compiler might use characters in that name > that you're not allowed to use in a name in C++ (g++ uses a . in > the name, for example), and its very likely that the compiler > generates a different name each time it recompiles the source > (true with both Sun CC and g++). > I think I understand now. In rough terms, the compiler generates a name for each namespace that the linker can then use to link up matching namespaces. In the anonymous namespace case, the compiler still generates that name (and thus it has external linkage), but because that name is not visible to the user (and the generation of that name is implementation specific), then in practice you can't really refer to the anonyous namespace. If you had the access to the generated name and the algorithm that generates it, you could do something like this (in pseudo-code terms): using inverse_generate_name(generated_anonymous_name_fro m file 1) Sound about right ?Taras |
![]() |
| Thread Tools | |
| Display Modes | |
In an effort to better serve ads to our visitors, cookies are used on objectmix.com. For more information, check out our Privacy Policy.