Creare ed usare Librerie dinamiche C

di il
19 risposte

Creare ed usare Librerie dinamiche C

Salve a tutti,sono un pò di giorni che sto comattendo con le librerie dinamiche in C. Vi espongo il mio problema: devo creare una mia libreria dinamica che va a includere dei miei file ed altri file provenienti da altre due librerie esistenti. Creata questa mia libreria dovrei avere la possibilità di usarla poi in ogni mio file eseguibile.
Ciò che ho fatto è questo:
#Compile My source
gcc -I$2 -I$2/applib/ -I$4/bp/include -I$4/bp/library -Lusr/lib -c src/*.csrc/bp_implementations/*.c -ldtnapi -lbp -lici
#Extract source from library of dtn2
cp $2/applib/libdtnapi.a .
ar x libdtnapi.a
#Create a dynamic library of ion
gcc -fPIC -shared -o libbp.so $4/bp/i86-redhat/libbp.o $4/bp/i86-redhat/libbpP.o $4/bp/i86-redhat/ecos.o $4/bp/i86-redhat/bei.o $4/bp/i86-redhat/extbsputil.o $4/bp/i86-redhat/extbspbab.o $4/bp/i86-redhat/extbsppcb.o $4/bp/i86-redhat/extbsppib.o $4/bp/i86-redhat/crypto.o $4/bp/i86-redhat/libbpnm.o
#Create my shared library
gcc -fPIC -shared *.o libbp.so -o libbp_abstraction_layer.so
Tutto ciò mi va a buon fine. Dopo scrivo il mio programma di prova e lo compilo nel seguente modo
gcc main.c -shared -O3 -o provaBP -L$BPDIR -I$DTN2DIR/applib -I$IONDIR/include -I$IONDIR/library -I$DTN2DIR -I$BPDIR/src/bp_implementations -I$BPDIR/src -ldtnapi -lbp -lici -lbp_abstraction_layer -lpthread
Ed anche questa compilazione va a buon fine. Ma quando provo ad eseguire ottengo il seguente errore:
Istruzione non consentita (core dump creato)
Ho provato a scrivere nel file di main una semplice printf e comunque ottengo l'errore di segmentazione.
Dove sbaglio o che altra soluzione potrei trovare?
Vi ringrazio in anticipo.

19 Risposte

  • Re: Creare ed usare Librerie dinamiche C

    Ciao annettaws,
    
    ar x libdtnapi.a
    
    Quali sono gli oggetti estratti qui? Sono compilati con -fPIC?
  • Re: Creare ed usare Librerie dinamiche C

    ixamit ha scritto:


    Ciao annettaws,
    
    ar x libdtnapi.a
    
    Quali sono gli oggetti estratti qui? Sono compilati con -fPIC?


    Sono dei file *.o e suppongo siano compilati con -fPIC, ad ogni modo non dovrei ricompilarli perchè è una libreria non creata da me.
    Ho provato a compilare senza l'opzione -shared nell'ultimo comando gcc: se all'interno del mio file eseguibile di prova non uso nessuna API della mia libreria tutto funziona, ma se provo ad usarne una ottengo questi errori :
    /home/annetta/DTN/bp_abstraction_layer/bp_abstraction_layer/libbp_abstraction_layer.so: undefined reference to `getOwnNodeNbr'
    /home/annetta/DTN/bp_abstraction_layer/bp_abstraction_layer/libbp_abstraction_layer.so: undefined reference to `parseEidString'
    /home/annetta/DTN/bp_abstraction_layer/bp_abstraction_layer/libbp_abstraction_layer.so: undefined reference to `bp_ion_copy_eid'
    ed altri simili, ovvero nella mia libreria bp_abstraction_layer non ha riferimenti nè alle mie API (bp_ecc ) nè a quelle di una delle librerie che uso.
    Ho provato anche ad usare l'opzione -static ma ovviamente non ha i riferimenti della libreria ION che è una libreria dinamica.
    Non so dove sbaglio.
  • Re: Creare ed usare Librerie dinamiche C

    annettaws ha scritto:


    Sono dei file *.o e suppongo siano compilati con -fPIC, ad ogni modo non dovrei ricompilarli perchè è una libreria non creata da me.
    Per cui rimangono statici

    Comunque,i passaggi corretti per creare una shared lib sono:
    
    % cd lib1
    % gcc -fPIC -c *.c
    
    % cd libn
    % gcc -fPIC -c *.c
    
    % gcc -o libfoo.so -shared lib1/*.o libn/*.o
    
    % copiala o crea un link simbolico nella tua /usr/lib
    
    % gcc -o mybin -lfoo ... ... ... ...
    
    
  • Re: Creare ed usare Librerie dinamiche C

    Ti faccio un esempio completo, dove b e c devono essere oggetti sharati:
    
    max@studio:~/foo> ll
    totale 12
    -rw-r--r-- 1 max users 48  2 nov 14.51 a.c
    -rw-r--r-- 1 max users 88  2 nov 14.50 b.c
    -rw-r--r-- 1 max users 87  2 nov 14.51 c.c
    max@studio:~/foo> cat *.c
    int main () {foo();bar ();return 0;} /* a.c */
    
    #include <stdio.h>               /* b.c */ 
    void foo () {puts ("HELLO\n"); } /* b.c */
    
    #include <stdio.h>               /* c.c */
    void bar () {puts ("WORLD\n"); } /* c.c */
    
    max@studio:~/foo> gcc -fPIC -c b.c
    max@studio:~/foo> gcc -fPIC -c c.c
    max@studio:~/foo> gcc -shared -o libfoo.so b.o c.o
    max@studio:~/foo> gcc a.c -L. -lfoo
    max@studio:~/foo> ldd ./a.out 
            linux-vdso.so.1 =>  (0x00007fffaed2c000)
            libfoo.so => not found
            libc.so.6 => /lib64/libc.so.6 (0x00007f7945d65000)
            /lib64/ld-linux-x86-64.so.2 (0x00007f79460d2000)
    max@studio:~/foo>
    max@studio:~/foo> LD_LIBRARY_PATH=. ldd ./a.out 
            linux-vdso.so.1 =>  (0x00007fff381ff000)
            libfoo.so => ./libfoo.so (0x00007f3abfdb5000)
            libc.so.6 => /lib64/libc.so.6 (0x00007f3abfa48000)
            /lib64/ld-linux-x86-64.so.2 (0x00007f3abffb7000)
    max@studio:~/foo> 
    
    edit:
    Per link-are anche lib statiche:
    
    gcc a.c -L. -lfoo -lm -lX11 -lvattelapesca
    
  • Re: Creare ed usare Librerie dinamiche C

    Penso di aver creato correttamente le librerie, direi che è solo un problema di link, perchè ho provato a modificare la lista delle librerie in questo modo :
    gcc main.c -o provaBP -L$BPDIR -I$DTN2DIR/applib -I$IONDIR/include -I$IONDIR/library -I$DTN2DIR -I$BPDIR/src/bp_implementations -I$BPDIR/src -lbp_abstraction_layer -ldtnapi -lbp -lici -lpthread
    mettendo per prima la mia libreria e poi le altre librerie ( che poi non capisco se già le linko quando creo la mia libreria perchè le devo indicare anche successivamente ? ), ed ottengo errori di "undefined reference" solo per le mie api :
    /home/annetta/DTN/bp_abstraction_layer/bp_abstraction_layer/libbp_abstraction_layer.so: undefined reference to `bp_ion_find_registration'
    /home/annetta/DTN/bp_abstraction_layer/bp_abstraction_layer/libbp_abstraction_layer.so: undefined reference to `bp_free_payload'
    /home/annetta/DTN/bp_abstraction_layer/bp_abstraction_layer/libbp_abstraction_layer.so: undefined reference to `bp_dtn_set_payload'
    /home/annetta/DTN/bp_abstraction_layer/bp_abstraction_layer/libbp_abstraction_layer.so: undefined reference to `bp_dtn_error'
    /home/annetta/DTN/bp_abstraction_layer/bp_abstraction_layer/libbp_abstraction_layer.so: undefined reference to `bp_dtn_open_with_IP'
    ecc...
    ho provato anche a compilare il main con una semplice printf senza alcun utilizzo delle mie api e la compilazione va a buon fine. Ho eseguito:
    ldd provaBP
    ottenendo
    linux-gate.so.1 =>  (0xb76f5000)
    libc.so.6 => /lib/i386-linux-gnu/libc.so.6 (0xb7530000)
    /lib/ld-linux.so.2 (0xb76f6000)
    non dovrei avere i riferimenti anche alle librerie indicate nel comando gcc ?
  • Re: Creare ed usare Librerie dinamiche C

    Penso di aver creato correttamente le librerie, direi che è solo un problema di link,
    Mi dai per cortesia solo la sequenza dove crei la tua libreria sharata? Te lo chiedo perché hai un riferimento non definito in fase di link e ldd non mostra nessun oggetto condiviso ma solo il link/loader.

    EDIT:
    mettendo per prima la mia libreria e poi le altre librerie ( che poi non capisco se già le linko quando creo la mia libreria perchè le devo indicare anche successivamente ? ), ed ottengo errori di "undefined reference" solo per le mie api :
    Cosa significa che le linki quando crei la libreria? NON DEVI LINKARLE
  • Re: Creare ed usare Librerie dinamiche C

    Riporto l'intero file di script :
    #Compile source
    	gcc -I$2 -I$2/applib/ -I$4/bp/include -I$4/bp/library -Lusr/lib -fPIC -c src/bp_implementations/*.c -lbp -lici -ldtnapi
    	gcc -I$DIR_BP_IMPL -I$2 -I$2/applib/ -I$4/bp/include -I$4/bp/library -Lusr/lib -fPIC -c src/*.c -lbp -lici -ldtnapi
    #extract source from dtn2's library
    	cp $2/applib/libdtnapi.a .
    	ar x libdtnapi.a
    #create a dynamic library of ion
    	gcc -fPIC -shared -o libbp.so $4/bp/i86-redhat/libbp.o $4/bp/i86-redhat/libbpP.o $4/bp/i86-redhat/ecos.o $4/bp/i86-redhat/bei.o $4/bp/i86-redhat/extbsputil.o $4/bp/i86-redhat/extbspbab.o $4/bp/i86-redhat/extbsppcb.o $4/bp/i86-redhat/extbsppib.o $4/bp/i86-redhat/crypto.o $4/bp/i86-redhat/libbpnm.o
    #create bp_abstraction_layer library
    	ar crs libbp_abstraction_layer.a *.o
    	gcc -fPIC -shared -o libbp_abstraction_layer.so *.o
    	rm libdtnapi.a
  • Re: Creare ed usare Librerie dinamiche C

    Ti avevo già risposto (ecco svelato l'arcano delle librerie). Devi toglierle dalla compilazione dell'oggetto
    
    #Compile source
    gcc -fPIC -c -I$2 -I$2/applib/ -I$4/bp/include -I$4/bp/library src/bp_implementations/*.c
    gcc  -fPIC -c -I$DIR_BP_IMPL -I$2 -I$2/applib/ -I$4/bp/include -I$4/bp/library src/*.c 
    Questa parte deve essere necessariamente statica perché non compilato con PIC (Position Independent Code)
    
    #extract source from dtn2's library
       cp $2/applib/libdtnapi.a .
       ar x libdtnapi.a
    
    Qui devi semplicemente crearti la libreria sharata dagli oggetti. Togli fPic ma assicurati che in lista ci siano solo gli oggetti compilati con -fpic
    
    #create a dynamic library of ion
       gcc -fPIC -shared -o libbp.so $4/bp/i86-redhat/libbp.o $4/bp/i86-redhat/libbpP.o $4/bp/i86-redhat/ecos.o $4/bp/i86-redhat/bei.o $4/bp/i86-redhat/extbsputil.o $4/bp/i86-redhat/extbspbab.o $4/bp/i86-redhat/extbsppcb.o $4/bp/i86-redhat/extbsppib.o $4/bp/i86-redhat/crypto.o $4/bp/i86-redhat/libbpnm.o
    

    Esegui il linker come hai fatto nel post precedente.
    EDIT:
    
    gcc main.c -o provaBP -L$BPDIR -I$DTN2DIR/applib -I$IONDIR/include -I$IONDIR/library -I$DTN2DIR -I$BPDIR/src/bp_implementations -I$BPDIR/src -lbp_abstraction_layer -ldtnapi -lbp -lici -lpthread
    
    Fai attenzione al percorso della shared object aggiungi -L/path/to/libdir_so
  • Re: Creare ed usare Librerie dinamiche C

    Ho modificato come mi hai suggerito, ma ancora facendo ldd sulla libreria libbp_abstraction_layer.so ottengo solo :
    linux-gate.so.1 =>  (0xb77d0000)
    libc.so.6 => /lib/i386-linux-gnu/libc.so.6 (0xb75f9000)
    /lib/ld-linux.so.2 (0xb77d1000)
    e compilando il main ancora gli stessi errori :
    gcc main.c -o provaBP -L$BPDIR -I$BPDIR/src/bp_implementations -I$BPDIR/src -I$DTN2DIR -I$DTN2DIR/applib -I$IONDIR/include -I$IONDIR/library -lbp_abstraction_layer -ldtnapi -lbp -lici -lpthread
    /home/annetta/DTN/bp_abstraction_layer/bp_abstraction_layer/libbp_abstraction_layer.so: undefined reference to `bp_ion_open_with_IP'
    /home/annetta/DTN/bp_abstraction_layer/bp_abstraction_layer/libbp_abstraction_layer.so: undefined reference to `bp_ion_errno'
    /home/annetta/DTN/bp_abstraction_layer/bp_abstraction_layer/libbp_abstraction_layer.so: undefined reference to `bp_dtn_copy_eid'
    /home/annetta/DTN/bp_abstraction_layer/bp_abstraction_layer/libbp_abstraction_layer.so: undefined reference to `bp_ion_recv'
    /home/annetta/DTN/bp_abstraction_layer/bp_abstraction_layer/libbp_abstraction_layer.so: undefined reference to `bp_dtn_send'
    /home/annetta/DTN/bp_abstraction_layer/bp_abstraction_layer/libbp_abstraction_layer.so: undefined reference to `bp_dtn_register'
    /home/annetta/DTN/bp_abstraction_layer/bp_abstraction_layer/libbp_abstraction_layer.so: undefined reference to `bp_dtn_build_local_eid'
    
    Ti riporto il codice shell della creazione della libreria
    
    #Compile source
    	gcc -I$2 -I$2/applib/ -I$4/bp/include -I$4/bp/library -fPIC -c src/bp_implementations/*.c 
    	gcc -I$DIR_BP_IMPL -I$2 -I$2/applib/ -I$4/bp/include -I$4/bp/library -fPIC -c src/*.c 
    #extract source from dtn2's library
    	cp $2/applib/libdtnapi.a .
    	ar x libdtnapi.a
    #create a dynamic library of ion
    	gcc -shared -o libbp.so $4/bp/i86-redhat/libbp.o $4/bp/i86-redhat/libbpP.o $4/bp/i86-redhat/ecos.o $4/bp/i86-redhat/bei.o $4/bp/i86-redhat/extbsputil.o $4/bp/i86-redhat/extbspbab.o $4/bp/i86-redhat/extbsppcb.o $4/bp/i86-redhat/extbsppib.o $4/bp/i86-redhat/crypto.o $4/bp/i86-redhat/libbpnm.o
    #create bp_abstraction_layer library
    	ar crs libbp_abstraction_layer.a *.o
    	gcc -fPIC -shared -o libbp_abstraction_layer.so *.o
    	rm libdtnapi.a
  • Re: Creare ed usare Librerie dinamiche C

    E il link dove sarebbe nello script?
  • Re: Creare ed usare Librerie dinamiche C

    e il link dove sarebbe nello script?
    sta in un altro file shell comunque il comando di link che uso è questo :
    gcc main.c -o provaBP -L$BPDIR  -I$BPDIR/src/bp_implementations -I$BPDIR/src -I$DTN2DIR -I$DTN2DIR/applib -I$IONDIR/include -I$IONDIR/library -lbp_abstraction_layer -lbp -lici -lpthread
  • Re: Creare ed usare Librerie dinamiche C

    Ci siamo quasi

    Mi devi illuminare su questo:
    
    #create bp_abstraction_layer library
       ar crs libbp_abstraction_layer.a *.o
       gcc -fPIC -shared -o libbp_abstraction_layer.so *.o
    
    dove lo compili e come

    per ultimo dobbiamo esser certi che il linker acceda all'oggetto sharato e non statico, per cui controlla che non ci sia la stessa libreria con un estensione statica
  • Re: Creare ed usare Librerie dinamiche C

    ixamit ha scritto:


    Ci siamo quasi

    Mi devi illuminare su questo:
    
    #create bp_abstraction_layer library
       ar crs libbp_abstraction_layer.a *.o
       gcc -fPIC -shared -o libbp_abstraction_layer.so *.o
    
    dove lo compili e come
    Ho due file shell di compilazione uno dove è compilato il main e l'altro dove faccio tutto il resto, cioè cerco di creare questa libreria.
    Ho eliminato la creazione della libreria statica ( ar crs libbp_abstraction_layer.a *.o ) e nada sempre lo stesso errore.
    Comunque avevo letto che se ci sono due librerie con lo stesso nome gcc prende la dinamica, ad ogni modo l'ho tolta.
    Il fatto è che mi dà errore di riferimento indefinito solo sulle api di 2 file.Ti spiego come è fatto il mio progetto: in /src ho un file dove definisco delle api "grigie" che poi richiamano altre funzioni definite in file che si trovano in src/bp_implementations. E' solo su quest'ultime che mi viene dato l'errore.
    ( cmq grazie davvero tanto per l'aiuto )
  • Re: Creare ed usare Librerie dinamiche C

    Ho due file shell di compilazione uno dove è compilato il main e l'altro dove faccio tutto il resto, cioè cerco di creare questa libreria.
    E' difficile comprendere, in quanto non si capisce da dove vengono gli oggetti in questione, cioè compilando senza avere una lista visibile dei sorgenti. Non è certo una situazione felice
    Ho eliminato la creazione della libreria statica ( ar crs libbp_abstraction_layer.a *.o ) e nada sempre lo stesso errore.
    Ok, ma gli oggetti che usi per costruirti libbp_abstraction_layer.so come sono stati compilati? devi usare la stessa logica che abbiamo usato per libbp.so. Per cui:
    1) li compili con -fpic
    2) crei l'oggetto sharato con gcc -shared -o libbp_abstraction_layer.so oggetto1.o ... oggettoN.o
    Comunque avevo letto che se ci sono due librerie con lo stesso nome gcc prende la dinamica, ad ogni modo l'ho tolta.
    Forse hai ragione. Io mi sono semplificato la vita con libtool e molte cose le ho dimenticate.

    Dai, riprova che la strada è giusta
    Nel caso ci fosse qualche altro problema che non vedo fai un COMMIT di tutto l'ambiente su github (mi sembra che sei registrato) e lo guardo meglio.
Devi accedere o registrarti per scrivere nel forum
19 risposte