Trying to create a Makefile that compiles C source into a .o file in a subfolder as well as creating the executable in a different subfolder depending on the architecture of the host PC. When I run "make" from a terminal window, make correctly compiles the first .c file into a .o and places the .o in the correct directory. However, when make tries to use the .o to create the executable, make complains that it cannot find the .o file. However, if I run make again, it finds the .o file and creates the executable in the correct folder. I am using vpath to indicate where to find the .o file and the executable. How can I fix this so make finds the .o file on the first run? Here is the Makefile:
# Makefile for helloword1 & helloworld2 programs
#
CFLAGS=-Wall
CC=gcc
ARCH=$(shell arch)
# set path to .o files
vpath %.o ./obj/$(ARCH)
# set path to executable files
vpath % ./bin/$(ARCH)
# The default target
all: helloworld1 helloworld2
# generic rule for compiling .c to .o
%.o : %.c
$(CC) $< -c $(CFLAGS) -o ./obj/$(ARCH)/$@
# generic rule for creating executable
%: %.o
$(CC) $< -o ./bin/$(ARCH)/$@
helloworld1: helloworld1.o
helloworld2: helloworld2.o
clean:
-rm -f ./obj/$(ARCH)/*.o ./bin/$(ARCH)/*
Here is make console output:
les@DV5590-LM22:~/C-Programs/makefile_play$ make
gcc helloworld1.c -c -Wall -o ./obj/x86_64/helloworld1.o
gcc helloworld1.o -o ./bin/x86_64/helloworld1
/usr/bin/ld: cannot find helloworld1.o: No such file or directory
collect2: error: ld returned 1 exit status
make: *** [Makefile:25: helloworld1] Error 1
les@DV5590-LM22:~/C-Programs/makefile_play$ make
gcc ./obj/x86_64/helloworld1.o -o ./bin/x86_64/helloworld1
gcc helloworld2.c -c -Wall -o ./obj/x86_64/helloworld2.o
gcc helloworld2.o -o ./bin/x86_64/helloworld2
/usr/bin/ld: cannot find helloworld2.o: No such file or directory
collect2: error: ld returned 1 exit status
make: *** [Makefile:25: helloworld2] Error 1
les@DV5590-LM22:~/C-Programs/makefile_play$ make
gcc ./obj/x86_64/helloworld2.o -o ./bin/x86_64/helloworld2
les@DV5590-LM22:~/C-Programs/makefile_play$
$(patsubst). Also, you probably want$(CC) -dumpmachinerather than justarch.patsubstis not portable even across Linuxes.makefilehas variables, why not use them? likeARCH = shell(cmd);PATH = my_path;$CC -c $ARCH/$PATH. or something.vpathmakes life easier when you need it. Claiming that it is useless is just wrong.ARCH = shell(cmd)is syntactically incorrect, plus theshellfunction is a GNU make feature, not POSIX.