By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
429,327 Members | 2,661 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 429,327 IT Pros & Developers. It's quick & easy.

Why no compilation error.

P: n/a
We have three files a.c, b.c and main.c respectively as follows:
a.c
---
int a;
b.c
---
int a = 10;
main.c
------
extern int a;
int main()
{
printf("a = %d\n",a);
return 0;
}
Let's see what happens, when the files are compiled together:
bash$ gcc a.c b.c main.c
bash$ ./a.out
a = 10
Hmm!! no compilation/linker error!!! Why is it so??

Sep 20 '06 #1
Share this Question
Share on Google+
14 Replies


P: n/a
On 19 Sep 2006 22:12:12 -0700, "sunny" <su*******@gmail.comwrote in
comp.lang.c:
We have three files a.c, b.c and main.c respectively as follows:
a.c
---
int a;
b.c
---
int a = 10;
main.c
------
extern int a;
int main()
{
printf("a = %d\n",a);
return 0;
}
Let's see what happens, when the files are compiled together:
bash$ gcc a.c b.c main.c
bash$ ./a.out
a = 10
Hmm!! no compilation/linker error!!! Why is it so??
Your program produces undefined behavior by having more than one
definition of an external object. The compiler is free to do anything
it wants. Once you generate undefined behavior, the C language no
longer places any requirements on the results.

--
Jack Klein
Home: http://JK-Technology.Com
FAQs for
comp.lang.c http://c-faq.com/
comp.lang.c++ http://www.parashift.com/c++-faq-lite/
alt.comp.lang.learn.c-c++
http://www.contrib.andrew.cmu.edu/~a...FAQ-acllc.html
Sep 20 '06 #2

P: n/a
Can anyone give a nice link of how these example works?

Jack Klein wrote:
On 19 Sep 2006 22:12:12 -0700, "sunny" <su*******@gmail.comwrote in
comp.lang.c:
We have three files a.c, b.c and main.c respectively as follows:
a.c
---
int a;
b.c
---
int a = 10;
main.c
------
extern int a;
int main()
{
printf("a = %d\n",a);
return 0;
}
Let's see what happens, when the files are compiled together:
bash$ gcc a.c b.c main.c
bash$ ./a.out
a = 10
Hmm!! no compilation/linker error!!! Why is it so??

Your program produces undefined behavior by having more than one
definition of an external object. The compiler is free to do anything
it wants. Once you generate undefined behavior, the C language no
longer places any requirements on the results.

--
Jack Klein
Home: http://JK-Technology.Com
FAQs for
comp.lang.c http://c-faq.com/
comp.lang.c++ http://www.parashift.com/c++-faq-lite/
alt.comp.lang.learn.c-c++
http://www.contrib.andrew.cmu.edu/~a...FAQ-acllc.html
Sep 20 '06 #3

P: n/a
Jack Klein wrote:
"sunny" <su*******@gmail.comwrote in comp.lang.c:
We have three files a.c, b.c and main.c respectively as follows:
a.c
---
int a;
b.c
---
int a = 10;
main.c
------
extern int a;
int main()
{
printf("a = %d\n",a);
return 0;
}
Let's see what happens, when the files are compiled together:
bash$ gcc a.c b.c main.c
Note: gcc has not been invoked as a conforming compiler, so you
can't have any expectations under the C language standard.
bash$ ./a.out
a = 10
Hmm!! no compilation/linker error!!! Why is it so??

Your program produces undefined behavior by having more than one
definition of an external object. The compiler is free to do anything
it wants. Once you generate undefined behavior, the C language no
longer places any requirements on the results.
Or, to more accurately answer the OP's question, the behaviour is UB
by 6.9p5, however that paragraph is not one of the listed Contraints
for 6.9 [pp2-3], so no diagnostic is required.

Why it's not a constraint, I don't know.

--
Peter

Sep 20 '06 #4

P: n/a
Peter Nilsson wrote:
Jack Klein wrote:
"sunny" <su*******@gmail.comwrote in comp.lang.c:
We have three files a.c, b.c and main.c respectively as follows:
a.c
---
int a;
b.c
---
int a = 10;
main.c
------
extern int a;
int main()
{
printf("a = %d\n",a);
return 0;
}
Let's see what happens, when the files are compiled together:
bash$ gcc a.c b.c main.c

Note: gcc has not been invoked as a conforming compiler, so you
can't have any expectations under the C language standard.
bash$ ./a.out
a = 10
Hmm!! no compilation/linker error!!! Why is it so??
Your program produces undefined behavior by having more than one
definition of an external object. The compiler is free to do anything
it wants. Once you generate undefined behavior, the C language no
longer places any requirements on the results.

Or, to more accurately answer the OP's question, the behaviour is UB
by 6.9p5, however that paragraph is not one of the listed Contraints
for 6.9 [pp2-3], so no diagnostic is required.

Why it's not a constraint, I don't know.
I imagine it's not a constraint because depending on the system, it may
not have an easy way to tell this apart from a definition whose name
matches that of a library function provided as an extension. In other
words, it could also generate a diagnostic for this legitimate code:

#include <stdio.h>
void write(char *s) { puts(s); }
int main(void) {
write("Hello, world!");
}

Sep 20 '06 #5

P: n/a
Hi All
but i get the compilation error if i initialize the variable "a" in a.c
ie.
// in a.c
int a = 200;

// in b.c
int a = 10.

on compilation, now i got multiple definition error.
may on first i.e uninitialized "a" will be stored in BSS section and
intialized "a" (a = 10) is stored in DS(data segment). so when i
intialize "a" in a.c
it will move to DS where it confilicts with "a" from b.c;

is it correct?

Peter Nilsson wrote:
Jack Klein wrote:
"sunny" <su*******@gmail.comwrote in comp.lang.c:
We have three files a.c, b.c and main.c respectively as follows:
a.c
---
int a;
b.c
---
int a = 10;
main.c
------
extern int a;
int main()
{
printf("a = %d\n",a);
return 0;
}
Let's see what happens, when the files are compiled together:
bash$ gcc a.c b.c main.c

Note: gcc has not been invoked as a conforming compiler, so you
can't have any expectations under the C language standard.
bash$ ./a.out
a = 10
Hmm!! no compilation/linker error!!! Why is it so??
Your program produces undefined behavior by having more than one
definition of an external object. The compiler is free to do anything
it wants. Once you generate undefined behavior, the C language no
longer places any requirements on the results.

Or, to more accurately answer the OP's question, the behaviour is UB
by 6.9p5, however that paragraph is not one of the listed Contraints
for 6.9 [pp2-3], so no diagnostic is required.

Why it's not a constraint, I don't know.

--
Peter
Sep 20 '06 #6

P: n/a
On 19 Sep 2006 23:59:33 -0700, "sunny" <su*******@gmail.comwrote in
comp.lang.c:
Hi All
but i get the compilation error if i initialize the variable "a" in a.c
ie.
// in a.c
int a = 200;

// in b.c
int a = 10.

on compilation, now i got multiple definition error.
may on first i.e uninitialized "a" will be stored in BSS section and
intialized "a" (a = 10) is stored in DS(data segment). so when i
intialize "a" in a.c
it will move to DS where it confilicts with "a" from b.c;

is it correct?
It is not correct. It is not incorrect. Once you produce undefined
behavior, the C standard no longer specifies what the program must do.
As far as the C language is concerned, anything that happens is just
as correct or incorrect as anything else.

You have broken a rule of C programming. Don't do that. Then you
won't have to worry whether what happens is correct.

--
Jack Klein
Home: http://JK-Technology.Com
FAQs for
comp.lang.c http://c-faq.com/
comp.lang.c++ http://www.parashift.com/c++-faq-lite/
alt.comp.lang.learn.c-c++
http://www.contrib.andrew.cmu.edu/~a...FAQ-acllc.html
Sep 20 '06 #7

P: n/a
"sunny" <su*******@gmail.comwrites:
We have three files a.c, b.c and main.c respectively as follows:
a.c
---
int a;
b.c
---
int a = 10;
main.c
------
extern int a;
int main()
{
printf("a = %d\n",a);
return 0;
}
Let's see what happens, when the files are compiled together:
bash$ gcc a.c b.c main.c
bash$ ./a.out
a = 10
Hmm!! no compilation/linker error!!! Why is it so??
With gnu linker, use -Wl,--warn-common. That's the (sloppy) common unix
practice.

A+

--
Jean-Marc
Sep 20 '06 #8

P: n/a
The variable is defined / initialised in two separate files. Each of
these C files will be compiled to object code. At the linking phase,
the linker usually has a specific order in which it searches for
external symbols, e.g. start with all the objects/libraries in current
folder in alphabetical order, followed by the so-called default paths
where other libraries and objects may reside. All the linkers I've
used, by default, will stop looking for an external reference if one
has already been found in an object or a library. Therefore, in this
case, it so happened that the linker encountered the definition with
initialisation first, hence the value 10 is displayed at execution. I
suppose a closer investigation of the linker properties would provide a
clear answer to this issue. Changing the initialisation from one file
to the other may exhibit a different behaviour (or at least I expect
to).

Romeo Ghiriti

Sep 20 '06 #9

P: n/a
The variable is defined / initialised in two separate files. Each of
these C files will be compiled to object code. At the linking phase,
the linker usually has a specific order in which it searches for
external symbols, e.g. start with all the objects/libraries in current
folder in alphabetical order, followed by the so-called default paths
where other libraries and objects may reside. All the linkers I've
used, by default, will stop looking for an external reference if one
has already been found in an object or a library. Therefore, in this
case, it so happened that the linker encountered the definition with
initialisation first, hence the value 10 is displayed at execution. I
suppose a closer investigation of the linker properties would provide a
clear answer to this issue. Changing the initialisation from one file
to the other may exhibit a different behaviour (or at least I expect
to).

Romeo Ghiriti

Sep 20 '06 #10

P: n/a
deepak wrote:
Can anyone give a nice link of how these example works?
Please don't top-post. Your replies belong following or interspersed
with properly trimmed quotes. See the majority of other posts in the
newsgroup, or:
<http://www.caliburn.nl/topposting.html>
Sep 20 '06 #11

P: n/a
sunny wrote:
Hi All
Please don't top-post. Your replies belong following or interspersed
with properly trimmed quotes. See the majority of other posts in the
newsgroup, or:
<http://www.caliburn.nl/topposting.html>
Sep 20 '06 #12

P: n/a
Default User <de***********@yahoo.comwrote:
Please don't top-post.
Wouldn't the [TPA] be better placed at the beginning of the post title
rather than the end?

--
C. Benson Manica | I *should* know what I'm talking about - if I
cbmanica(at)gmail.com | don't, I need to know. Flames welcome.
Sep 20 '06 #13

P: n/a
"Amigo" <rg******@hotmail.comwrites:
The variable is defined / initialised in two separate files. Each of
these C files will be compiled to object code. At the linking phase,
the linker usually has a specific order in which it searches for
external symbols, e.g. start with all the objects/libraries in current
folder in alphabetical order, followed by the so-called default paths
where other libraries and objects may reside. All the linkers I've
used, by default, will stop looking for an external reference if one
has already been found in an object or a library. Therefore, in this
case, it so happened that the linker encountered the definition with
initialisation first, hence the value 10 is displayed at execution. I
suppose a closer investigation of the linker properties would provide a
clear answer to this issue. Changing the initialisation from one file
to the other may exhibit a different behaviour (or at least I expect
to).
I think you are confusing two issues. A linker will not import an object
file if it doesn't provides some undefined symbol. (That's one way for
providing extensions in a library and still beeing able to use those
symbols in user programs; another way -- which is mandatory for dynamic
library which can't be broken into parts -- is to use something like elf's
weak symbols).

When the linker has decided that an object must be part of the image (and
all linkers I know consider that all object files directly given on the
command line are in that class), the linkers give error message for
duplicate definitions. Unix linker traditionnaly don't give such error
message when all but one of the definitions are tentative definitions.

Yours,

--
Jean-Marc
Sep 20 '06 #14

P: n/a
Christopher Benson-Manica wrote:
Default User <de***********@yahoo.comwrote:
Please don't top-post.

Wouldn't the [TPA] be better placed at the beginning of the post title
rather than the end?
Why? Where do I put it, before the "Re:"? Just after? I'm flexible, but
the end made more sense and is slightly easier to do, as it's easy it
position the cursor at the end accurately.

It's there so that people who want to filter can. The filter probably
doesn't care where it is.

Brian
Sep 20 '06 #15

This discussion thread is closed

Replies have been disabled for this discussion.