scope of variable in c project

Thread Starter

King2

Joined Jul 17, 2022
80
I'm experimenting with what I came up with about the scope of variables in the C language.

By definition extern variable can be accessible in another files. in my code extern variable is defined in source.c file and I want to access it in source1. C file but I can't access the extern variable in source1.c files.

I have compiled the code on Visual Studio

source.c

C:
#include<stdio.h>

/* file scope begin for source.c file */

int Global_Variable = 2;

static int Static_Global_Variable = 3;

extern int Extern_Variable = 4;

/* local scope begin for foo */
void foo()
{

    int  LOCAL_Variable = 10;           
    int  Static_LOCAL_Variable = 11;

    printf("Global Variable in foo = %d \n", Global_Variable);
    printf("Static Global Variable in foo = %d \n", Static_Global_Variable);
    printf("Extern Variable in foo = %d \n", Extern_Variable);

    printf("LOCAL Variable = %d \n", LOCAL_Variable);
    printf("Static LOCAL Variable = %d \n", Static_LOCAL_Variable);

} /* local scope end for foo*/   


/* local scope begin for main */
int main()
{
    int Variable = 1;                 

    printf("Variable in main = %d \n", Variable);

    printf("Global Variable in main = %d \n", Global_Variable);

    printf("Static Global Variable in main = %d \n", Static_Global_Variable);

    printf("Extern Variable in main = %d \n", Extern_Variable);

    printf("\n");
    foo();

    return 0;
} /* local scope end for main*/

/* file scope end for source.c file  */
source1.c

C:
#include<stdio.h>
void calculation()
{
    printf("Extern Variable in main = %d \n", Extern_Variable);
    printf("Global Variable in main = %d \n", Global_Variable);
}
Output terminal

Program show error "identifier "Extern_Variable" is undefined Project1"

1664107195477.png
 
Last edited:

MrChips

Joined Oct 2, 2009
27,122
In general, you want to avoid using global variables.
Pass the value or address of the variable in the function parameter list instead.
 

Thread Starter

King2

Joined Jul 17, 2022
80
You need to declare the variable in source1.c like this:

extern int Extern_Variable;
Why do I need to declare in source1.c file while I have already declared in source.c file?

If the extern variable is declared in one source file, we can access it in another source file, this is what the definition says:
 

MrChips

Joined Oct 2, 2009
27,122
Why do I need to declare in source1.c file while I have already declared in source.c file?

If the extern variable is declared in one source file, we can access it in another source file, this is what the definition says:
Because source1.c does not know where the variable is located.
 

WBahn

Joined Mar 31, 2012
27,395
The "extern" modifier says that you are declaring the name of a variable, but that that variable is defined in an outer scope.

Thus, in the file that you define the value (which means that memory is allocated), you should NOT use the extern keyword. Most compilers will give you a warning about the variable both being defined (due to being initialized) and being declared 'extern'.

So source.c should have

int Extern_Variable = 4;

while source1.c should have

extern int Extern_Variable;
 
Last edited:

WBahn

Joined Mar 31, 2012
27,395
Why do I need to declare in source1.c file while I have already declared in source.c file?

If the extern variable is declared in one source file, we can access it in another source file, this is what the definition says:
This is NOT what the definition (i.e., language specification) says.

Consider the following:

C:
// ==================================
// main.c
// ==================================

#include <stdio.h>
#include <stdlib.h>

// These prototypes would normally be in header files
void f_fred(void);
void f_fred2(void);
void f_fred3(void);
void f_sue(void);

int fred = 12;
extern int sue;

int main(void) 
{
    f_fred();
    f_fred2();
    f_fred3();
    f_sue();
    printf("[%p] %10i main:fred\n", &fred, fred);
    printf("[%p] %10i main:sue\n", &sue, sue);
    return 0;
}

// ==================================
// fred.c
// ==================================

#include <stdio.h>

static int fred = 42;

void f_fred(void)
{
    extern int fred;
    fred += 10;
    printf("[%p] %10i f_fred:fred\n", &fred, fred);
}

void f_fred2(void)
{
    static int fred = 142;
    fred += 10;
    printf("[%p] %10i f_fred2:fred\n", &fred, fred);
}

void f_fred3(void)
{
    fred += 10;
    printf("[%p] %10i f_fred3:fred\n", &fred, fred);
}
This is what results when compiled and run:

Code:
[0000000000403010]         52 f_fred:fred
[0000000000403014]        152 f_fred2:fred
[0000000000403010]         62 f_fred3:fred
[0000000000407970]         10 f_sue:sue
[0000000000403020]         12 main:fred
[0000000000407970]         10 main:sue
Notice that the variable 'fred' in f_fred() and f_fred3() both refer to the static variable defined at the top of fred.c.

If you change the 'fred' in main to declare it as external linkage (the same way that 'sue' is right beneath it), then you will get a linker error because there is no definition in any file of 'fred' with external linkage.
 

Thread Starter

King2

Joined Jul 17, 2022
80
So source.c should have

int Extern_Variable = 4;

while source1.c should have

extern int Extern_Variable;
Error in source1 files

Error C4430 missing type specifier - int assumed. Note: C++ does not support default-int Project1
Error C2365 'printf': redefinition; previous definition was 'function' Project1
Error (active) E0077 this declaration has no storage class or type specifier Project1


source1.cpp
C:
#include<stdio.h>

extern int Extern_Variable;
printf("Extern Variable in source1 = %d \n", Extern_Variable);
source.cpp
C:
#include<stdio.h>

/* file scope begin for source.c file */

int Global_Variable = 2;   

static int Static_Global_Variable = 3;     

extern int Extern_Variable = 4;

/* local scope begin for foo */
void foo() 
{

    int  LOCAL_Variable = 10;                 
    int  Static_LOCAL_Variable = 11; 

    printf("Global Variable in foo = %d \n", Global_Variable);
    printf("Static Global Variable in foo = %d \n", Static_Global_Variable);
    printf("Extern Variable in foo = %d \n", Extern_Variable);
    
    printf("LOCAL Variable = %d \n", LOCAL_Variable);
    printf("Static LOCAL Variable = %d \n", Static_LOCAL_Variable);

} /* local scope end for foo*/         


/* local scope begin for main */
int main()   
{
    int Variable = 1;                       

    printf("Variable in main = %d \n", Variable);

    printf("Global Variable in main = %d \n", Global_Variable);
    
    printf("Static Global Variable in main = %d \n", Static_Global_Variable);

    printf("Extern Variable in main = %d \n", Extern_Variable);
    
    printf("\n");
    foo();

    return 0;
} /* local scope end for main*/

/* file scope end for source.c file  */
 

Thread Starter

King2

Joined Jul 17, 2022
80
Line 9 in source.cpp
Remove extern.
code compile without error but I don't understand what's wrong with source1.c file I don't get print statement inside file on screen
C:
#include<stdio.h>

/* file scope begin for source.c file */

int Global_Variable = 2;  

static int Static_Global_Variable = 3;    

int Extern_Variable = 4;

/* local scope begin for foo */
void foo()
{

    int  LOCAL_Variable = 10;                
    int  Static_LOCAL_Variable = 11;

    printf("Global Variable in foo = %d \n", Global_Variable);
    printf("Static Global Variable in foo = %d \n", Static_Global_Variable);
    printf("Extern Variable in foo = %d \n", Extern_Variable);
   
    printf("LOCAL Variable = %d \n", LOCAL_Variable);
    printf("Static LOCAL Variable = %d \n", Static_LOCAL_Variable);

} /* local scope end for foo*/        


/* local scope begin for main */
int main()  
{
    int Variable = 1;                      

    printf("Variable in main = %d \n", Variable);

    printf("Global Variable in main = %d \n", Global_Variable);
   
    printf("Static Global Variable in main = %d \n", Static_Global_Variable);

   
    printf("\n");
    foo();

    return 0;
} /* local scope end for main*/

/* file scope end for source.c file  */
source1.c
C:
#include<stdio.h>

extern int Extern_Variable;


void foo1()
{
    printf("hello");
    printf("Extern Variable in source1 = %d \n", Extern_Variable);
}
Terminal Output

Code:
Variable in main = 1
Global Variable in main = 2
Static Global Variable in main = 3

Global Variable in foo = 2
Static Global Variable in foo = 3
Extern Variable in foo = 4
LOCAL Variable = 10
Static LOCAL Variable = 11
 

Thread Starter

King2

Joined Jul 17, 2022
80
You never called foo1( ).
Thank you very much. now the problem is solved
Output
Code:
Variable in main = 1
Global Variable in main = 2
Static Global Variable in main = 3

Global Variable in foo = 2
Static Global Variable in foo = 3
Extern Variable in foo = 4
LOCAL Variable = 10
Static LOCAL Variable = 11
hello
Extern Variable in source1 = 4
source.c
C:
#include<stdio.h>

/* file scope begin for source.c file */

int Global_Variable = 2;  

static int Static_Global_Variable = 3;    

int Extern_Variable = 4;

void foo1();

/* local scope begin for foo */
void foo()
{

    int  LOCAL_Variable = 10;                
    int  Static_LOCAL_Variable = 11;

    printf("Global Variable in foo = %d \n", Global_Variable);
    printf("Static Global Variable in foo = %d \n", Static_Global_Variable);
    printf("Extern Variable in foo = %d \n", Extern_Variable);
   
    printf("LOCAL Variable = %d \n", LOCAL_Variable);
    printf("Static LOCAL Variable = %d \n", Static_LOCAL_Variable);

} /* local scope end for foo*/        


/* local scope begin for main */
int main()  
{
    int Variable = 1;                      

    printf("Variable in main = %d \n", Variable);

    printf("Global Variable in main = %d \n", Global_Variable);
   
    printf("Static Global Variable in main = %d \n", Static_Global_Variable);

   
    printf("\n");
    foo();
    foo1();

    return 0;
} /* local scope end for main*/

/* file scope end for source.c file  */
source1.c
C:
#include<stdio.h>

extern int Extern_Variable;


void foo1()
{
    printf("hello \n");
    printf("Extern Variable in source1 = %d \n", Extern_Variable);
}
 

Thread Starter

King2

Joined Jul 17, 2022
80
Because source1.c does not know where the variable is located.
This is NOT what the definition (i.e., language specification) says.
I am getting confused in between definition and declaration. I don't see any difference between them.

Whenever a variable has to be declared, I write the data type in front of the variable name, so the compiler allocates memory for the variable.

Can you explain how definition is different from declaration
 

MrChips

Joined Oct 2, 2009
27,122
int my_variable;

is declaring my_variable in the specified scope.
If it is declared outside of all functions then it is a global variable.

If you wish to access my_variable from another source, don’t declare it again. It already has been declared.

You notify the linker that my_variable can be found during linking time.
Use,
extern int my_variable;

It is good practice to put all external declarations in a .h file.

#define my_constant 123
uses text substitution. It replaces ever occurance of my_constant with “123” prior to compilation.
 

WBahn

Joined Mar 31, 2012
27,395
I am getting confused in between definition and declaration. I don't see any difference between them.

Whenever a variable has to be declared, I write the data type in front of the variable name, so the compiler allocates memory for the variable.

Can you explain how definition is different from declaration
A variable declaration just informs the compiler that a variable of a particular name and type is going to be used. It doesn't actually result in any storage being allocated for it.

A variable definition tells the compiler to actually cause memory to be allocated and associated with that particular name.

Most of the time you define variables. But if you want to refer to a variable that would otherwise not be visible to the compiler, such as a file-scope variable in another file, you need to declare the variable.

Remember, the source code files can be compiled individually and in any order. So if you define a variable in another file, you need to put something into each of the other files that need to refer to that variable. That is the purpose of the 'extern' keyword. Think of that keyword as saying, "Hey, compiler, don't worry that this variable isn't defined in this file. Trust me that it is defined in another file in such a way that when you get around to linking all of the files together to create the final executable that you will be able to find it."
 

WBahn

Joined Mar 31, 2012
27,395
int my_variable;

is declaring my_variable in the specified scope.
If it is declared outside of all functions then it is a global variable.

If you wish to access my_variable from another source, don’t declare it again. It already has been declared.

You notify the linker that my_variable can be found during linking time.
Use,
extern int my_variable;

It is good practice to put all external declarations in a .h file.

#define my_constant 123
uses text substitution. It replaces ever occurance of my_constant with “123” prior to compilation.
int my_variable;

is DEFINING the variable.

extern int my_variable;

would be DECLARING the variable.

It's easy to get the terms swapped or get sloppy with them. The way to remember is that, like a dictionary, a proper definition leaves nothing unstated. Specifically, if you define a variable, you are defining everything about it, including where it is stored.

Variables and functions can be declared multiple times -- that is almost always what happens when you include a header file -- but every variable or function that is used must be defined exactly once.
 
Top