Jump to content
  • Advertisement
Sign in to follow this  
gasto

Extern block scope variable?

This topic is 2060 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

int i = 4;
int main(int argc, char* argv[])
{
    extern int i;
    cout << i;
    return 0;
}

 

In Visual Studio 2008 outputs

4

without warnings.

 

What is going on? Weren't block scope variables supposed to have no linkage?

I suspect the compiler is ignoring the fact that it is in a block altogether and simply redeclaring the global ivariable(applying internal linkage.)

Share this post


Link to post
Share on other sites
Advertisement

extern int i;

 

isn't a stack variable it's just telling the compiler you know that an int named i has a definition elsewhere. It doesn't even need to be defined in the same translation unit, the linker will find it if it's unique (and has external linkage).

 

You may not even get an error if i isn't really an int though.

 

EDIT: It's not good practice to extern variables at block scope, since if you do it more than once you have to change all occurrences if you change the type. You should only extern things in a single header file.

 

EDIT2: extern NEVER allocates any storage, it's just a way to tell the compiler and linker you know that something exists and has an address somewhere.

Edited by Paradigm Shifter

Share this post


Link to post
Share on other sites
Also, and rather spectatularly as you tagged it as "c language"

That is **NOT** C.

Check your compiler options, double-check that you are compiling as C rather than C++.

Share this post


Link to post
Share on other sites

It could be C if cout is in scope and of integral type, cout << i; but it wouldn't have any useful side effects though, so would be optimised away ;)

Edited by Paradigm Shifter

Share this post


Link to post
Share on other sites
int i = 4;
int main(int argc, char* argv[])
{
    extern int i;
    cout << i;
    return 0;
}

What is going on? Weren't block scope variables supposed to have no linkage?

 

 

"int i =4" is not a block scope but whole file scope(it is even more than file scope because it is by default external)  * and "extern int i;" is a symbol declaration (not needed at all here) 

 

* a normal 'global' aso someone could name it, ane "extern int i" is 

this time not needed declaration ("part of a header" just info to the linker, nothing binary) - it is usable if you remove i to another .obj module then it is used by linker to allow you tu use that from this place 

Edited by fir

Share this post


Link to post
Share on other sites

That is correct but it will still work if i is not in file scope but has external linkage. Not recommended though, because of the don't repeat yourself idiom.

 

This would work too (also not good practice):

int main(int argc, char* argv[])
{
    extern int i;
    cout << i;
    return 0;
}
 
int i = 4;
Edited by Paradigm Shifter

Share this post


Link to post
Share on other sites

EDIT2: extern NEVER allocates any storage, it's just a way to tell the compiler and linker you know that something exists and has an address somewhere.

This is incorrect. Extern does allocate storage when used together with an initializer in global scope. It defines a global variable, just like any (non-static) variable defined in global scope.
 
EDIT: added a detail

Share this post


Link to post
Share on other sites

 

EDIT2: extern NEVER allocates any storage, it's just a way to tell the compiler and linker you know that something exists and has an address somewhere.

This is incorrect. Extern does allocate storage when used together with an initializer in global scope. It defines a global variable, just like any (non-static) variable defined in global scope.
 
EDIT: added a detail

 

Actually that throws a linker error:

Beginning.obj : error LNK2005: "int i" (?i@@3HA) already defined in otherFile.obj

Share this post


Link to post
Share on other sites

Basically what I've come to learn about this compiler is that it allows multiple declarations but not multiple definitions.

Share this post


Link to post
Share on other sites

Basically what I've come to learn about this compiler is that it allows multiple declarations but not multiple definitions.

 

ofcourse, you could populete a declaration 1000 times with no trouble

but populating a definition will raise a symbole conflict

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

GameDev.net is your game development community. Create an account for your GameDev Portfolio and participate in the largest developer community in the games industry.

Sign me up!