1
votes

I'm trying to use GCC (linux) with a makefile to compile my project. I get the following error

"No rule to make target 'output/src/main.o', needed by 'test'.  Stop."

This is the makefile:

COMPILE_PREX ?= 
CC = $(COMPILE_PREX)gcc

SOURCE = $(wildcard src/*.c)
OBJS = $(addprefix ./output/, $(patsubst %.c, %.o, $(SOURCE)))

INCLUDES = -I ./src
CFLAGS += -O2 -Wall -g
LDFLAGS += -lpthread

TARGET = test

$(TARGET): $(OBJS)
    $(CC) $(OBJS) $(LDFLAGS) -o $(TARGET)

%.o: %.c
    @mkdir -p ./output
    $(CC) $(CFLAGS) $(INCLUDES) -o $(addprefix ./output/, $@) -c $< 

clean:
    rm -rf ./output
1
You are lying to make. The %.o: %.c rule does not create $@ (which you promised), but ./output/$@ (which is the lie).Jens
What should I do if I want to output the *.o to ./output/?corey chang
Does changing the rule to output/%.o: src/%.c work? This also needs $(CC) .... -o $@ -c $<.Jens
I'm trying, but it doesn't work.corey chang
Ok, the next step on Stackoverflow would be to upvote and accept the answer that helped you.Jens

1 Answers

1
votes

This should work. Note the use of mkdir $(@D) to create output directories as needed.

COMPILE_PREX ?=
CC = $(COMPILE_PREX)gcc

SOURCE = $(wildcard src/*.c)
OBJS = $(addprefix output/, $(patsubst %.c, %.o, $(SOURCE)))

INCLUDES = -I src
CFLAGS += -O2 -Wall -g
LDFLAGS += -lpthread

TARGET = test

$(TARGET): $(OBJS)
    $(CC) $(OBJS) $(LDFLAGS) -o $(TARGET)

output/%.o: %.c
    @mkdir -p $(@D)
    $(CC) $(CFLAGS) $(INCLUDES) -o $@ -c $<

clean:
    rm -rf output

Running it here with make clean test:

rm -rf output
gcc -O2 -Wall -g -I src -o output/src/hello.o -c src/hello.c
gcc output/src/hello.o -lpthread -o test