2013-01-19 17 views
9

Rozważmy program Hello World C:Jak określić, które opcje wiersza poleceń gcc domyślnie przechodzą na ld?

hello.c:

#include "stdio.h" 

int main() 
{ 
     printf("Hello, World!\n"); 
} 

Gdybym zadzwonić:

$ gcc -c hello.c -o hello.o 

To będzie produkować plik ELF relocatable hello.o

Jeśli zadzwonię:

$ gcc hello.o -o hello   [1] 

To będzie link hello.o z LD i produkują plik wykonywalny ELF cześć

Jednak jeśli zadzwonię ld bezpośrednio [2] zamiast [1]:

$ ld hello.o -o hello    [2] 

otrzymuję te błędy:

/usr/bin/ld.bfd.real: warning: cannot find entry symbol _start 
test.c:(.text+0xa): undefined reference to `puts' 

gcc musi przekazywać inne opcje do ld (na przykład do łączenia biblioteki C).

Czy jest mimo to ustalenie, co dokładnie przechodzi gcc z linii poleceń na ld w komendzie [1]?

Odpowiedz

15

Tak, można użyć linii gcc -v hello.o -o hello, aby uzyskać linię łącza. Dla Państwa przykład na moim komputerze ubuntu, mam tę linię łącza (red być MultiLine dla czytelności):

/usr/lib/gcc/x86_64-linux-gnu/4.4.5/collect2 
--build-id 
--eh-frame-hdr 
-m elf_x86_64 
--hash-style=gnu 
-dynamic-linker 
/lib64/ld-linux-x86-64.so.2 
-o hello 
-z relro 
/usr/lib/gcc/x86_64-linux-gnu/4.4.5/../../../../lib/crt1.o 
/usr/lib/gcc/x86_64-linux-gnu/4.4.5/../../../../lib/crti.o 
/usr/lib/gcc/x86_64-linux-gnu/4.4.5/crtbegin.o 
-L/usr/lib/gcc/x86_64-linux-gnu/4.4.5 
-L/usr/lib/gcc/x86_64-linux-gnu/4.4.5 
-L/usr/lib/gcc/x86_64-linux-gnu/4.4.5/../../../../lib 
-L/lib/../lib 
-L/usr/lib/../lib 
-L/usr/lib/gcc/x86_64-linux-gnu/4.4.5/../../.. -L/usr/lib/x86_64-linux-gnu 
hello.o 
-lgcc 
--as-needed -lgcc_s --no-as-needed 
-lc 
-lgcc 
--as-needed -lgcc_s --no-as-needed 
/usr/lib/gcc/x86_64-linux-gnu/4.4.5/crtend.o 
/usr/lib/gcc/x86_64-linux-gnu/4.4.5/../../../../lib/crtn.o 

Zauważ, że collect2 jest tylko aliasem ld.

+1

Wydaje się, że na moim Ubuntu 12.10 64 pole 'collect2' nie jest prostym aliasem dla' ld'. 'collect2' jest plikiem wykonywalnym, podczas gdy' ld' jest łączem sym do 'ld.bfd', który jest dowiązaniem symbolicznym do' hardened-ld', który jest skryptem perl. Nie mam pojęcia, co się tam dzieje. –

+1

Przepraszam, nie mam na myśli dosłownego aliasu. Przekonasz się, że jeśli uruchomisz to samo polecenie z 'ld' zamiast tego będzie działać tak samo. Dokumenty: http://gcc.gnu.org/onlinedocs/gcc-4.3.5/gccint/Collect2.html –

+0

Jaka jest różnica między 'collect2' a' ld'? Nie można zrozumieć łatwo po przeczytaniu gccint. –