1

consider the following simple makefile

CC=gcc 
CFLAGS=-I.

all: hellomake

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


hellofunc.o: hellofunc.c hellomake.h    
    $(CC) -c hellofunc.c -o hellofunc.o $(CFLAGS)

hellomake: hellomake.o hellofunc.o  
    $(CC) -o hellomake hellomake.o hellofunc.o


clean:  rm hellomake *.o

In this case, the variable $(CFLAGS) has to be included at the end in order to include the .h files (in this case hellomake.h). However, in the following makefile, it is not necessary, the variable gets appendend automatically

CC=gcc
CFLAGS=-I.

hellomake: hellomake.o hellofunc.o
    $(CC) -o hellomake hellomake.o hellofunc.o

My question is, in which cases does the CFLAGS get appended? why is not like this on the first code snippet? thank you!

learning_dude
  • 1,030
  • 1
  • 5
  • 10
  • 1
    In your second case (second makefile) you don't have compilation step (this is the place where `h` files are used). You are simply linking things that were build in the past. This is why `gcc` doesn't care about `-I.` – Oo.oO Jan 17 '20 at 12:38
  • BTW, the link rule would be better written as `$(LINK.o) $^ $(LDLIBS) -o $@` (copying the built-in `%:%.o` rule, except for the obsolete `$(LOADLIBES)`). That will help when you add linker flags or extra libraries. And it saves you having to repeat the object file names, too. – Toby Speight Jan 17 '20 at 13:08

1 Answers1

3

In your second example, you are relying on a built-in rule for the %.o: %.c case, and that rule uses $(CFLAGS).

If you are using GNU Make, you can dump its built-in stuff using make -qp. When I do that, I get a rule

%.o: %.c
#  commands to execute (built-in):
    $(COMPILE.c) $(OUTPUT_OPTION) $<

which refers to this, higher up in the listing:

COMPILE.c = $(CC) $(CFLAGS) $(CPPFLAGS) $(TARGET_ARCH) -c
Ture Pålsson
  • 6,088
  • 2
  • 12
  • 15