2012-05-17 19 views
7

Sto lavorando a un progetto che utilizza i file .c e .cu. Il pacchetto originale era interamente scritto in C e aveva il suo Makefile (funzionava perfettamente). Ho aggiunto il file .cu al progetto e ora voglio modificare il Makefile in modo che compili tutto insieme.Makefile per CUDA e C

Ecco il mio tentativo:

CC = nvcc 

SOURCEDIR = ../sourcedir 

EXE = it 

#C_SOURCES = $(wildcard $(SOURCEDIR)/*.c) 
#CU_SOURCES = $(wildcard $(SOURCEDIR)/*.cu) 

SOURCES = $(SOURCEDIR)/it.c \ 
      $(SOURCEDIR)/em.c \ 
      $(SOURCEDIR)/art.c \ 
      $(SOURCEDIR)/cg.c \ 
      $(SOURCEDIR)/amatrix.c \ 
      $(SOURCEDIR)/itreadargs.c \ 
      $(SOURCEDIR)/sparse.c \ 
      $(SOURCEDIR)/misc.c \ 
      $(SOURCEDIR)/eval.c \ 
      $(SOURCEDIR)/imgtools.c \ 
      $(SOURCEDIR)/calc.c \ 
      $(SOURCEDIR)/egif_lib.c \ 
      $(SOURCEDIR)/dgif_lib.c \ 
      $(SOURCEDIR)/gif_err.c \ 
      $(SOURCEDIR)/gif_hash.c 

CU_SOURCES = $(SOURCEDIR)/cg_cuda.cu 

H_FILES = $(wildcard $(IDIR)/*.h) 

IDIR  = -I../include 

OBJS  = $(SOURCES:.c=.o) 
CU_OBJS = $(CU_SOURCES:.cu=.o) 

CFLAGS  = -O3 
#-finline-functions -Winline -Wall -falign-loops=2 -falign-jumps=2 -falign-functions=2 -Wstrict-prototypes 

NVCCFLAGS = -arch=sm_20 

#CFLAGS  = -g -Wstrict-prototypes -Winline -Wall 

LFLAGS  = -lm 


$(EXE) : $(OBJS) $(CU_OBJS) 
    $(CC) $(CFLAGS) $(NVCCFLAGS) -o [email protected] $? 

$(SOURCEDIR)/%.o : $(SOURCEDIR)/%.c $(H_FILES) 
    $(CC) $(CFLAGS) $(IDIR) -c -o [email protected] $< 

$(SOURCEDIR)/%.o : $(SOURCEDIR)/%.cu $(H_FILES) 
    $(CC) $(NVCCFLAGS) $(IDIR) -c -o [email protected] $< 


clean: 
    rm -f $(OBJS) $(EXE) 

La struttura del progetto è la seguente:

  • Progetto
    • includono
    • sourcedir
    • si
    • altre cartelle

dove includere ha tutti i file .he sourcedir ha il file .CU (c'è un solo file di .cu) .c e; it ha il Makefile.

Il problema con il mio Makefile è che quando faccio rendere nella cartella si ricevo un sacco di errori che mi dice che il file che ha la funzione main() (it.c in sourcedir cartella) non viene collegato a nessuna delle funzioni di altre librerie. Lo stesso vale per il mio file .cu.

Potete per favore darmi qualche suggerimento su cosa potrebbe essere sbagliato con il mio Makefile? Ho usato come riferimento il seguente post StackOverflow: makefile for C++/CUDA project

Grazie per il vostro aiuto,
Vlad

EDIT:
Ecco l'originale Makefile, quella che ha lavorato sui file .c. Puoi aiutarmi con quello che devo aggiungere in modo che il file .cu sia compilato insieme agli altri? Grazie ancora. EDIT

CC = gcc 

SOURCEDIR = ../sourcedir 

EXE = it 

SOURCES = $(SOURCEDIR)/it.c \ 
      $(SOURCEDIR)/em.c \ 
      $(SOURCEDIR)/art.c \ 
      $(SOURCEDIR)/cg.c \ 
      $(SOURCEDIR)/amatrix.c \ 
      $(SOURCEDIR)/itreadargs.c \ 
      $(SOURCEDIR)/sparse.c \ 
      $(SOURCEDIR)/misc.c \ 
      $(SOURCEDIR)/eval.c \ 
      $(SOURCEDIR)/imgtools.c \ 
      $(SOURCEDIR)/calc.c \ 
      $(SOURCEDIR)/egif_lib.c \ 
      $(SOURCEDIR)/dgif_lib.c \ 
      $(SOURCEDIR)/gif_err.c \ 
      $(SOURCEDIR)/gif_hash.c 

IDIR  = -I../include 

OBJS  = $(SOURCES:.c=.o) 

CFLAGS  = -O3 -finline-functions -Winline -Wall -falign-loops=2 -falign-jumps=2 -falign-functions=2 -Wstrict-prototypes 

#CFLAGS  = -g -Wstrict-prototypes -Winline -Wall 

LFLAGS  = -lm 


$(EXE) : $(OBJS) 
    $(CC) $(CFLAGS) -o $(EXE) $(OBJS) $(LFLAGS) 

%.o : %.c 
    $(CC) -c $(IDIR) $(CFLAGS) $< -o [email protected] 

clean: 
    rm -f $(OBJS) $(EXE) 

DOPO:
ho cambiato il Makefile ancora un po ', ripulito un po', e ora ho solo un paio di errori che sono legati al fatto che il br non è sempre legata alla .c file e viceversa.

CC := gcc 

SOURCEDIR := ../sourcedir 

EXE := it 

SOURCES := $(SOURCEDIR)/it.c \ 
      $(SOURCEDIR)/em.c \ 
      $(SOURCEDIR)/art.c \ 
      $(SOURCEDIR)/cg.c \ 
      $(SOURCEDIR)/amatrix.c \ 
      $(SOURCEDIR)/itreadargs.c \ 
      $(SOURCEDIR)/sparse.c \ 
      $(SOURCEDIR)/misc.c \ 
      $(SOURCEDIR)/eval.c \ 
      $(SOURCEDIR)/imgtools.c \ 
      $(SOURCEDIR)/calc.c \ 
      $(SOURCEDIR)/egif_lib.c \ 
      $(SOURCEDIR)/dgif_lib.c \ 
      $(SOURCEDIR)/gif_err.c \ 
      $(SOURCEDIR)/gif_hash.c 

CU_SOURCES := $(SOURCEDIR)/cg_cuda.cu 

IDIR  := ../include 

INCLUDES := -I../include 

H_FILES := $(IDIR)/analyze.h \ 
      $(IDIR)/calc.h \ 
      $(IDIR)/eval.h \ 
      $(IDIR)/gif_hash.h \ 
      $(IDIR)/gif_lib.h \ 
      $(IDIR)/imgtools.h \ 
      $(IDIR)/iradon.h \ 
      $(IDIR)/iradoninc.h \ 
      $(IDIR)/it.h \ 
      $(IDIR)/itini.h \ 
      $(IDIR)/misc.h \ 
      $(IDIR)/sparse.h   

CFLAGS := -g -O3 

NVCCFLAGS := -g -G -O3 -arch=sm_20 

LDFLAGS  := -lGL -lGLU -lglut -lpthread -lcuda 

HOST_OBJ := $(SOURCES:.c=.c.o) 
DEVICE_OBJ := $(CU_SOURCES:.cu=.cu.o) 

%.c.o : %.c $(HFILES) 
    $(CC) -c $(INCLUDES) $(CFLAGS) $< -o [email protected] 

%.cu.o : %.cu $(H_FILES) 
    nvcc -c $(INCLUDES) $(NVFLAGS) $< -o [email protected] 


$(EXE): $(HOST_OBJ) $(DEVICE_OBJ) 
    nvcc $(NVFLAGS) $(LDFLAGS) $(INCLUDES) -o [email protected] $^ 

clean: 
    rm -f $(OBJS) $(EXE) 

Così ora sto ottenendo questi errori:

nvcc -lGL -lGLU -lglut -lpthread -lcuda -I../include -o it ../sourcedir/it.c.o ../sourcedir/em.c.o ../sourcedir/art.c.o ../sourcedir/cg.c.o ../sourcedir/amatrix.c.o ../sourcedir/itreadargs.c.o ../sourcedir/sparse.c.o ../sourcedir/misc.c.o ../sourcedir/eval.c.o ../sourcedir/imgtools.c.o ../sourcedir/calc.c.o ../sourcedir/egif_lib.c.o ../sourcedir/dgif_lib.c.o ../sourcedir/gif_err.c.o ../sourcedir/gif_hash.c.o ../sourcedir/cg_cuda.cu.o 
../sourcedir/it.c.o: In function `main': 
/home/vburca/CUDA_Research_2012/Recon2D/it/../sourcedir/it.c:280: undefined reference to `CG_CUDA' 
../sourcedir/cg_cuda.cu.o: In function `CGUpdateAddVector(Vector*, Vector*, Vector*, float)': 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x44): undefined reference to `Error(char*, ...)' 
../sourcedir/cg_cuda.cu.o: In function `CG_CUDA(SparseMatrix*, Vector*, Vector*)': 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x15f): undefined reference to `Print(int, char*, ...)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x18c): undefined reference to `ReadFIF(char*)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x1a2): undefined reference to `ImageToVector(Image*)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x1b8): undefined reference to `FreeImage(Image*)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x1c7): undefined reference to `DeviationVector(Vector*)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x248): undefined reference to `Print(int, char*, ...)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x255): undefined reference to `InitVector(int)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x269): undefined reference to `InitVector(int)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x27d): undefined reference to `InitVector(int)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x291): undefined reference to `InitVector(int)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x2a5): undefined reference to `InitVector(int)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x2c0): undefined reference to `Print(int, char*, ...)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x2e0): undefined reference to `MultSparseMatrixVector(SparseMatrix*, Vector*, Vector*)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x328): undefined reference to `MultSparseTMatrixVector(SparseMatrix*, Vector*, Vector*)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x37c): undefined reference to `MultSparseMatrixVector(SparseMatrix*, Vector*, Vector*)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x395): undefined reference to `MultVectorVector(Vector*, Vector*)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x3b1): undefined reference to `Print(int, char*, ...)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x3fb): undefined reference to `Print(int, char*, ...)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x414): undefined reference to `MultVectorVector(Vector*, Vector*)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x47b): undefined reference to `ConstrainVector(Vector*, float, float)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x4ce): undefined reference to `MultSparseTMatrixVector(SparseMatrix*, Vector*, Vector*)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x4e7): undefined reference to `MultVectorVector(Vector*, Vector*)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x55b): undefined reference to `MultSparseMatrixVector(SparseMatrix*, Vector*, Vector*)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x581): undefined reference to `SaveIteration(Vector*, int, char*)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x5ab): undefined reference to `L2NormVector(Vector*, Vector*, float)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x602): undefined reference to `Print(int, char*, ...)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x61f): undefined reference to `VectorToImage(Vector*, int, int)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x650): undefined reference to `L2NormVector(Vector*, Vector*, float)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x66a): undefined reference to `Print(int, char*, ...)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x679): undefined reference to `FreeVector(Vector*)' 
tmpxft_00004e1d_00000000-1_cg_cuda.cudafe1.cpp:(.text+0x69c): undefined reference to `RenameImage(Image*, char*)' 
collect2: ld returned 1 exit status 
make: *** [it] Error 1 

Grazie per la vostra pazienza leggendo il mio post.

+1

Sei sicuro che questo ha funzionato prima di aver introdotto il file '.cu'? Ad ogni modo, ti suggerisco di provare a cambiare '$?' In '$ ^'. – Beta

+0

Beh, l'ho cambiato; Posso anche postare il Makefile originale ... forse questo mi aiuterebbe con quello che dovrei aggiungere in modo che anche i file .cu si compilino. – vburca

+0

Non ci hai fornito abbastanza informazioni (ad es. Il messaggio di errore) per essere sicuri del problema esatto, ma hai apportato molte piccole modifiche tra questi due makefile. Prova una ricerca binaria: scrivi un makefile con solo metà di questi cambiamenti e verifica se funziona. Se trovi * un cambiamento * che fa la differenza, e non ha ancora senso, faccelo sapere. – Beta

risposta

2

Va bene, ci vorranno alcune iterazioni.Prova questo e commentare con i risultati:

CC = nvcc 

SOURCEDIR = ../sourcedir 

EXE = it 

SOURCES = $(SOURCEDIR)/it.c \ 
      $(SOURCEDIR)/em.c \ 
      $(SOURCEDIR)/art.c \ 
      $(SOURCEDIR)/cg.c \ 
      $(SOURCEDIR)/amatrix.c \ 
      $(SOURCEDIR)/itreadargs.c \ 
      $(SOURCEDIR)/sparse.c \ 
      $(SOURCEDIR)/misc.c \ 
      $(SOURCEDIR)/eval.c \ 
      $(SOURCEDIR)/imgtools.c \ 
      $(SOURCEDIR)/calc.c \ 
      $(SOURCEDIR)/egif_lib.c \ 
      $(SOURCEDIR)/dgif_lib.c \ 
      $(SOURCEDIR)/gif_err.c \ 
      $(SOURCEDIR)/gif_hash.c 

IDIR  = -I../include 

OBJS  = $(SOURCES:.c=.o) 

CFLAGS  = -O3 

NVCCFLAGS = -arch=sm_20 

LFLAGS  = -lm 

$(EXE) : $(OBJS) $(SOURCEDIR)/cg_cuda.o 
    $(CC) $(CFLAGS) -o [email protected] $^ $(LFLAGS) 

$(SOURCEDIR)/%.o : $(SOURCEDIR)/%.c 
    $(CC) $(NVCCFLAGS) $(IDIR) -c -o [email protected] $< 

$(SOURCEDIR)/%.o : $(SOURCEDIR)/%.cu $(H_FILES) 
    $(CC) $(NVCCFLAGS) $(IDIR) -c -o [email protected] $< 

clean: 
    rm -f $(OBJS) $(EXE) 

EDIT: turno 2
Ho modificato il makefile. Prova make clean ; make e nota il risultato. Quindi prova make ../sourcedir/cg_cuda.o.

EDIT: turno 3
Va bene, provare di nuovo: make clean ; make.

+0

fare: Attenzione: il file 'Makefile 'ha ora di modifica 3e + 02 s in futuro nvcc -O3 -o it ../sourcedir/it.o ../sourcedir/em.o ../sourcedir/art.o ../sourcedir/cg.o ../sourcedir/amatrix.o ../sourcedir/itreadargs.o ../sourcedir/sparse.o ../sourcedir/misc.o ../sourcedir/eval.o .. /sourcedir/imgtools.o ../sourcedir/calc.o ../sourcedir/egif_lib.o ../sourcedir/dgif_lib.o ../sourcedir/gif_err.o ../sourcedir/gif_hash.o -lm . ./sourcedir/it.o: nella funzione 'main ': it.c :(. testo + 0x188): riferimento non definito a' CG_CUDA' collect2: ld restituito 1 stato di uscita make: *** [it] Errore 1 – vburca

+0

La prima volta che ho eseguito, ho generato un sacco di avvertimenti e simili, ma la seconda volta ho ricevuto solo l'errore sopra riportato. – vburca

+0

Grazie mille per il tuo aiuto! – vburca