petajamaja
petajamaja

Reputation: 530

"make clean" causes "make all" failure

When I execute this Makefile without clean, it functions OK and both the shared library and the main executable are created correctly. However, when I add the clean target, the "make all" fails. What could be the reason?

CC = gcc
CFLAGS = -fPIC -Wall -Werror 
LDFLAGS = -shared  

TARGET_LIB= libnsd.so

lib: nsd.o nd.o
    $(CC) $(LDFLAGS) -o ${TARGET_LIB} nsd.o nd.o -lm

nd.o : nd.c nd.h
    $(CC) -c $(CFLAGS) nd.c

nsd.o : nsd.c nsd.h
    $(CC) -c $(CFLAGS) nsd.c

all: main.c
    $(CC) -o -I. -L. main.c  -lnsd

clean:
    rm -f libnsd.so nd.o nsd.o

Upvotes: 0

Views: 129

Answers (2)

MadScientist
MadScientist

Reputation: 100856

nos's answer is on the right track.

It only appeared to work before, because you happened to run make in the right order. It won't work after a clean operation because, as nos points out, you have not declared all of your prerequisites. The rule that links main.o must depend on the shared library target, so make knows the right order to build things.

Also, you REALLY want your targets to be the actual file you're building. If they're something else, then make will always think they're out of date even if you haven't changed anything, and always rebuild them.

Something like this will be better:

CC = gcc
CFLAGS = -fPIC -Wall -Werror
CPPFLAGS = -I.
LDFLAGS = -shared  

PROGRAM = main
TARGET_LIB= libnsd.so

all: $(PROGRAM)

$(PROGRAM): main.o $(TARGET_LIB)
        $(CC) -o $@ -L. main.o  -lnsd

$(TARGET_LIB): nsd.o nd.o
        $(CC) $(LDFLAGS) -o $@ nsd.o nd.o -lm

nd.o : nd.c nd.h
nsd.o : nsd.c nsd.h

clean:
        rm -f libnsd.so *.o

Upvotes: 2

nos
nos

Reputation: 229108

Your all: target needs to depend on the lib target, so the library is built first.

The -o argument to the compiler also needs a name for executable it should create.

all: lib main.c
    $(CC) -o main -I. -L. main.c  -lnsd

Normally you want the target name to be the file that you create, otherwise things get rebuilt when it's not needed. (the lib: target has the same issue) but as an exampe for the executable:

.PHONY: all
all: lib main

main: lib main.c
    $(CC) -o main -I. -L. main.c  -lnsd

Upvotes: 5

Related Questions