Abhijatya Singh
Abhijatya Singh

Reputation: 642

Defining variable in header file causes multiple variable definition

I was doing some test coding for generating the pattern base on given pattern string and done as follows:

The header file is test.h:

#ifndef test_h

#define test_h

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

extern char uid []= "123456789561";

void generate_uid(FILE *,char *, char);

#endif

The .c file are as follows: test.c

#include"test.h"

extern int count;

void generate_uid(FILE *fp,char *uid_t, char ch)
{
    int index = rand()%12;
    int i,j;

    strcpy(uid_t,uid);

    if(ch == ' ')
    {
        for(j=3;j<10;j+=6)
        {
            uid_t[j] = ch;
        }
    }
// Replace numbers with special chars or alphabets(small/capital)
    else
    {
        if(index < 6)
        {
            for(i=0;i<index;i++)
            {
                uid_t[i]=ch;
            }
        }   
        else
        {
            for(i=index;i<strlen(uid);i++)
            {
                uid_t[i]=ch;
            }
        }
    }
    count++;
    fprintf(fp,"\"%s\", ",uid_t);
        return;
}

main.c:

#include"test.h"

int count = 0;

int main()
{

    FILE *fp_char,*fp_test;

    char invalid_chars;
    char *uid_t = (char *)malloc(sizeof(char)*14);

    fp_char = fopen("invalidchars.txt","r");
    fp_test = fopen("uid_test.txt","w");

    if(fp_test == NULL || fp_char == NULL)
    {
        printf("cannot open file.\n");
        return;
    }

    while((invalid_chars = fgetc(fp_char)) != EOF) 
    {
        if(invalid_chars == '\n')
        {
            continue;
        }

        generate_uid(fp_test,uid_t, invalid_chars);

    }
        //Greater than 12 digit
        strcpy(uid_t,uid);
        strcat(uid_t,"2");
        count++;
        fprintf(fp_test,"\"%s\", ",uid_t);

        //Less than 12 digit
        strcpy(uid_t,uid);
        uid_t[11]='\0';
        count++;
        fprintf(fp_test,"\"%s\", ",uid_t);       



        count++;
        fprintf(fp_test,"\"%s\", ","NULL");
        count++;
        fprintf(fp_test,"\"%s\", ","empty");


    free(uid_t);
    fclose(fp_char);
    fclose(fp_test);
    printf("Number of string count : %d\n",count);
    return 0;
}

Makefile is:

all : test.o main.o run

run : test.o main.o
    $(CC) -g $^ -o $@

%.o : %.c
    ${CC} -g -c $< -o $@


.PHONY : clean

clean :
    -rm -f *.o run

When I was compiling it gives the following:

cc -g -c test.c -o test.o
cc -g -c main.c -o main.o
cc -g test.o main.o -o run
main.o:(.data+0x0): multiple definition of `uid'
test.o:(.data+0x0): first defined here
collect2: error: ld returned 1 exit status
make: *** [run] Error 1

Where I am going wrong.

Upvotes: 3

Views: 761

Answers (2)

Vlad from Moscow
Vlad from Moscow

Reputation: 310950

You defined in header object

extern char uid []= "123456789561";

and this definition now is present in each compilation unit where the header is included. So the same object is defined several times and the compiler issues an error.

You should declare it in the header as for example

extern char uid [13];

and define it in one of the modules

char uid []= "123456789561";

Upvotes: 0

Aracthor
Aracthor

Reputation: 5907

You can declare a global variable in a header file, but not attribute it a value, because you can do it only once. So if you include your test.h file in more than one .c file (that would be usual), your compiler will see many initializations of the same thing when it will assemble your .o files.

Let only that in your test.h file :

extern char uid [];

And in one specific .c file (like uid.c for instance), initalize it :

char uid []= "123456789561";

Then add this new file to your Makefile.

Upvotes: 3

Related Questions