Recently started C coding on Linux and ran into a 'multiple definition' error (sources A.c and B.c below)
gcc -Wall A.o B.o -o C
/usr/bin/ld: B.o: in function "Hello":
B.c:(.text+0x0): multiple definition of `Hello'; A.o:A.c:(.text+0x0): first defined here
Searching thru S.O, it was suggested to use this linker command line option
--allow-multiple-definition (-z muldefs)
Normally when a symbol is defined multiple times, the linker will report a fatal error.
These options allow multiple definitions and the first definition will be used.
Running this command bypassed the error message
gcc -Wall -Wl,--allow-multiple-definition A.o B.o -o C
It seemed peace was restored, however, it output
./C
Hello A
Hello A
World B
I was expecting this output below and "assumed" the linker would smoothly resolve any symbol conflicts, but at least keep the existing code functionality
Hello A
Hello B
World B
However, the resulting C ELF binary was modified as follows by examining the assembly output from objdump -S -M intel C
- Removed the duplicate Hello() in B.c
- Re-pointed any calls to Hello() in A.c
Questions
- Is renaming the symbol Hello() the only correct solution?
- Is it bad practice to use --allow-multiple-definition option?
- If possible, should the linker be more sentient about intended code functionality by restricting a functions visibility i.e., understand that Hello() is a duplicate symbol in B.o and calling it from World() should be confined to B.o instead of looking into A.o?
gcc -Wall -c A.c
#include <stdio.h> void Hello(void) { printf("Hello A\n"); } int main() { Hello(); World(); return 0; } gcc -Wall -c B.c
#include <stdio.h> void Hello(void) { printf("Hello B\n"); } void World(void) { Hello(); printf("World B\n"); } EDITED
Based upon the comments/answers, adding the static keyword worked nicely
static void Hello(void) { printf("Hello B\n"); } No need to use that command line option now
gcc -Wall A.o B.o -o C
Hello A
Hello B
World B
The real impetus for the question is that we build a UASM assembly object file, and given the tip about the C static keyword, at least I can now research what's available in UASM to make these functions PRIVATE to the object.
UPDATE
For UASM, was able to make the function scope limited to the object file by adding
PROC PRIVATE FRAME Thanks!
staticto the definitions ofHello.--allow-multiple-definitionoption ever got through code review...