Make: Compiling only one .c file though i modify the header file which is included in two .c files...
This question already has an answer here:
'make' does not recompile when source file has been edited
3 answers
I have two .c files and one .h file which is included in both .c files.
I have make file :
CC=gcc
CFLAGS=-I.
OBJ = hellofunc.o hellomake.o
DEPS := $(OBJ:.o=.d)
-include $(DEPS)
%.o: %.c
$(CC) $(CFLAGS) -MM -MT $@ -MF $(patsubst %.o,%.d,$@) $<
$(CC) -c -o $@ $< $(CFLAGS)
hellomake: hellomake.o hellofunc.o
$(CC) -o $@ $^
I modified hellomake.h header file and then ran above make file. It is compiling only the first file which is assigned to DEPS variable, Which is hellofunc.c
FYI, When i change the order of DEPS variable it is compiling hellomake.o , Seems like make is only picking first file assigned to DEPS variable.
Is there anything wrong in my makefile.. Please help.
makefile gnu-make
marked as duplicate by tripleee, Hovercraft Full Of Eels, Mike Kinghan, eyllanesc, ewolden Nov 21 '18 at 13:33
This question has been asked before and already has an answer. If those answers do not fully address your question, please ask a new question.
add a comment |
This question already has an answer here:
'make' does not recompile when source file has been edited
3 answers
I have two .c files and one .h file which is included in both .c files.
I have make file :
CC=gcc
CFLAGS=-I.
OBJ = hellofunc.o hellomake.o
DEPS := $(OBJ:.o=.d)
-include $(DEPS)
%.o: %.c
$(CC) $(CFLAGS) -MM -MT $@ -MF $(patsubst %.o,%.d,$@) $<
$(CC) -c -o $@ $< $(CFLAGS)
hellomake: hellomake.o hellofunc.o
$(CC) -o $@ $^
I modified hellomake.h header file and then ran above make file. It is compiling only the first file which is assigned to DEPS variable, Which is hellofunc.c
FYI, When i change the order of DEPS variable it is compiling hellomake.o , Seems like make is only picking first file assigned to DEPS variable.
Is there anything wrong in my makefile.. Please help.
makefile gnu-make
marked as duplicate by tripleee, Hovercraft Full Of Eels, Mike Kinghan, eyllanesc, ewolden Nov 21 '18 at 13:33
This question has been asked before and already has an answer. If those answers do not fully address your question, please ask a new question.
You have not declared any dependency onhellomake.h
so of course Make ignores it.
– tripleee
Nov 21 '18 at 11:32
@tripleee, Can you please give brief answer by updating my make file? I am new to make
– santosh
Nov 21 '18 at 11:39
I am including both hellomake.d , hellofunc.d files using include directive.. That should work right?
– santosh
Nov 21 '18 at 11:42
I think this question should not have been marked as duplicate of a the question cited by those who voted to close. This one makes use of automatic dependency generation. Manually adding header files to the prerequisites should not be needed.
– Renaud Pacalet
Nov 21 '18 at 14:40
add a comment |
This question already has an answer here:
'make' does not recompile when source file has been edited
3 answers
I have two .c files and one .h file which is included in both .c files.
I have make file :
CC=gcc
CFLAGS=-I.
OBJ = hellofunc.o hellomake.o
DEPS := $(OBJ:.o=.d)
-include $(DEPS)
%.o: %.c
$(CC) $(CFLAGS) -MM -MT $@ -MF $(patsubst %.o,%.d,$@) $<
$(CC) -c -o $@ $< $(CFLAGS)
hellomake: hellomake.o hellofunc.o
$(CC) -o $@ $^
I modified hellomake.h header file and then ran above make file. It is compiling only the first file which is assigned to DEPS variable, Which is hellofunc.c
FYI, When i change the order of DEPS variable it is compiling hellomake.o , Seems like make is only picking first file assigned to DEPS variable.
Is there anything wrong in my makefile.. Please help.
makefile gnu-make
This question already has an answer here:
'make' does not recompile when source file has been edited
3 answers
I have two .c files and one .h file which is included in both .c files.
I have make file :
CC=gcc
CFLAGS=-I.
OBJ = hellofunc.o hellomake.o
DEPS := $(OBJ:.o=.d)
-include $(DEPS)
%.o: %.c
$(CC) $(CFLAGS) -MM -MT $@ -MF $(patsubst %.o,%.d,$@) $<
$(CC) -c -o $@ $< $(CFLAGS)
hellomake: hellomake.o hellofunc.o
$(CC) -o $@ $^
I modified hellomake.h header file and then ran above make file. It is compiling only the first file which is assigned to DEPS variable, Which is hellofunc.c
FYI, When i change the order of DEPS variable it is compiling hellomake.o , Seems like make is only picking first file assigned to DEPS variable.
Is there anything wrong in my makefile.. Please help.
This question already has an answer here:
'make' does not recompile when source file has been edited
3 answers
makefile gnu-make
makefile gnu-make
asked Nov 21 '18 at 11:19
santoshsantosh
255
255
marked as duplicate by tripleee, Hovercraft Full Of Eels, Mike Kinghan, eyllanesc, ewolden Nov 21 '18 at 13:33
This question has been asked before and already has an answer. If those answers do not fully address your question, please ask a new question.
marked as duplicate by tripleee, Hovercraft Full Of Eels, Mike Kinghan, eyllanesc, ewolden Nov 21 '18 at 13:33
This question has been asked before and already has an answer. If those answers do not fully address your question, please ask a new question.
You have not declared any dependency onhellomake.h
so of course Make ignores it.
– tripleee
Nov 21 '18 at 11:32
@tripleee, Can you please give brief answer by updating my make file? I am new to make
– santosh
Nov 21 '18 at 11:39
I am including both hellomake.d , hellofunc.d files using include directive.. That should work right?
– santosh
Nov 21 '18 at 11:42
I think this question should not have been marked as duplicate of a the question cited by those who voted to close. This one makes use of automatic dependency generation. Manually adding header files to the prerequisites should not be needed.
– Renaud Pacalet
Nov 21 '18 at 14:40
add a comment |
You have not declared any dependency onhellomake.h
so of course Make ignores it.
– tripleee
Nov 21 '18 at 11:32
@tripleee, Can you please give brief answer by updating my make file? I am new to make
– santosh
Nov 21 '18 at 11:39
I am including both hellomake.d , hellofunc.d files using include directive.. That should work right?
– santosh
Nov 21 '18 at 11:42
I think this question should not have been marked as duplicate of a the question cited by those who voted to close. This one makes use of automatic dependency generation. Manually adding header files to the prerequisites should not be needed.
– Renaud Pacalet
Nov 21 '18 at 14:40
You have not declared any dependency on
hellomake.h
so of course Make ignores it.– tripleee
Nov 21 '18 at 11:32
You have not declared any dependency on
hellomake.h
so of course Make ignores it.– tripleee
Nov 21 '18 at 11:32
@tripleee, Can you please give brief answer by updating my make file? I am new to make
– santosh
Nov 21 '18 at 11:39
@tripleee, Can you please give brief answer by updating my make file? I am new to make
– santosh
Nov 21 '18 at 11:39
I am including both hellomake.d , hellofunc.d files using include directive.. That should work right?
– santosh
Nov 21 '18 at 11:42
I am including both hellomake.d , hellofunc.d files using include directive.. That should work right?
– santosh
Nov 21 '18 at 11:42
I think this question should not have been marked as duplicate of a the question cited by those who voted to close. This one makes use of automatic dependency generation. Manually adding header files to the prerequisites should not be needed.
– Renaud Pacalet
Nov 21 '18 at 14:40
I think this question should not have been marked as duplicate of a the question cited by those who voted to close. This one makes use of automatic dependency generation. Manually adding header files to the prerequisites should not be needed.
– Renaud Pacalet
Nov 21 '18 at 14:40
add a comment |
2 Answers
2
active
oldest
votes
As @tripleee noted in the comments, make
will by default build the first target it encounters. Since the include
files are included directly, as if they were cut-and-pasted in place, the first target in the first .d
file (which I'm guessing you'll find to be hellofunc.c
) is the first target that make
encounters, so that's what make
aims to build.
If you move the include
line to the end of the file, then the first target in the file will be hellomake
, and so that's the target make
will attempt to build by default.
Meta remark: if you can, I'd say it's better to avoid this pattern of depending on .d
files, and instead aim to express sufficiently many of the dependencies ‘by hand’ directly in the makefile. Doing it this .d
way does work (ie, I'm not saying what you're doing is wrong) and appears to be labour-saving, but in my experience it tends to be a little brittle, partly because if you don't have the .d
files to hand then you suddenly have zero dependencies. In order to have the .d
files to hand, you'll have to check them in to your code repository (you are using a repository, aren't you?), but that will mean they'll frequently be trivially out of date, and... it can turn into a bit of a mess.
If one .c file includes n number of header files .We can t specify them in our make files right? It looks bit ugly. Is there any simple way to handle this?
– santosh
Nov 21 '18 at 12:11
I disagree with the discussion about auto-generated prerequisites in the last paragraph above. They are actually perfectly reliable when done correctly (unfortunately because make is a generic tool, and not a tool specifically for working with C/C++ programs, doing it right takes a bit of work). Handling prerequisites by hand is fine in simple situations but it's simply untenable in any moderate to large program. See make.mad-scientist.net/papers/… for a discussion of how to do auto-dependency correctly (even if all .d files are removed!)
– MadScientist
Nov 21 '18 at 12:35
@MadScientist thanks for the opposing point of view, and the useful link. The 'a bit of work' and the length of that page, illustrate what I regard as the downside, and why I think of this approach as 'brittle' (in my experience) rather than wrong. I've tried multiple ways of managing this, over the years, with and without automake (and I'll read your page carefully), and concluded that make is one of those systems where 'mostly correct and readable/maintainable' is better than 'completely correct but write-only'. This is probably a style/taste issue, in the end.
– Norman Gray
Nov 21 '18 at 13:23
If you have 10 files with simple prerequisites, it's fine to list things by hand. In projects I work on we have over 1500 source files and over 1700 header files across many directories (and this is nowhere near a "large" project, really). It's C++ so there is a lot of recursive header file inclusion and there is simply no way to manage that by hand. The real problem is that if you forget to add a prerequisite to your makefile then your program can break in subtle and hard to understand ways. It's not just a compile error. An unreliable makefile is often WORSE than no makefile.
– MadScientist
Nov 21 '18 at 15:10
add a comment |
EDIT: considered MadScientist's comment and blog post about separate recipe for .d
files.
You could tell make how to generate the .d
files with a separate rule instead of putting this in another recipe (but see the above mentioned blog post for several reasons for not doing so).
And you should probably tell make that your default goal is hellomake
:
.DEFAULT_GOAL := hellomake
CC=gcc
CFLAGS=-I.
OBJ = hellofunc.o hellomake.o
DEPS := $(OBJ:.o=.d)
-include $(DEPS)
%.d: %.c
$(CC) $(CFLAGS) -MM -MT $@ -MF $@ $<
%.o: %.c
$(CC) -c -o $@ $< $(CFLAGS)
hellomake: hellomake.o hellofunc.o
$(CC) -o $@ $^
And it would probably be even better if you were letting make find the source files and deduce the rest:
.DEFAULT_GOAL := hellomake
CC := gcc
CFLAGS := -I.
SRCS := $(wildcard *.c)
OBJS := $(patsubst %.c,%.o,$(SRC))
DEPS := $(patsubst %.c,%.d,$(SRC))
-include $(DEPS)
%.d: %.c
$(CC) $(CFLAGS) -MM -MT $@ -MF $@ $<
%.o: %.c
$(CC) -c -o $@ $< $(CFLAGS)
hellomake: $(OBJS)
$(CC) -o $@ $^
Finally, following MadScientist's advices, a better, more efficient, less prone to failures solution could be:
.DEFAULT_GOAL := hellomake
CC := gcc
CFLAGS := -I.
SRCS := $(wildcard *.c)
OBJS := $(patsubst %.c,%.o,$(SRC))
DEPS := $(wildcard $(patsubst %.c,%.d,$(SRC)))
include $(DEPS)
%.o: %.c %.d
$(CC) -MT $@ -MMD -MP -MF $*.Td $(CFLAGS) -c -o $@ $<
mv -f $*.Td $*.d && touch $@
hellomake: $(OBJS)
$(CC) -o $@ $^
%.d: ;
.PRECIOUS: %.d
Ohh Got it. Thanks! Do we have any tutorials or articles for "-MM -MT" dependency options ? Can you please share if any ?
– santosh
Nov 21 '18 at 12:36
2
Actually creating a separate recipe for.d
files leads to a lot of unpleasant side-effects. The new modern (and best) method for creating prerequisite files is to create them as part of building the object file, not in a separate rule. See the blog post I lined to in comments above for a full discussion.
– MadScientist
Nov 21 '18 at 12:37
BTW, It didnt worked. I copied same make file content above. Still its comping only one .c file.
– santosh
Nov 21 '18 at 13:13
@santosh: are you sure both files include this header file? And did you check the content of the.d
files to verify that this header file is really listed as a dependency?
– Renaud Pacalet
Nov 21 '18 at 13:24
Yeah, I verified. I am including header file in both .c files. And .d files also has header file listed in it.
– santosh
Nov 21 '18 at 13:38
|
show 2 more comments
2 Answers
2
active
oldest
votes
2 Answers
2
active
oldest
votes
active
oldest
votes
active
oldest
votes
As @tripleee noted in the comments, make
will by default build the first target it encounters. Since the include
files are included directly, as if they were cut-and-pasted in place, the first target in the first .d
file (which I'm guessing you'll find to be hellofunc.c
) is the first target that make
encounters, so that's what make
aims to build.
If you move the include
line to the end of the file, then the first target in the file will be hellomake
, and so that's the target make
will attempt to build by default.
Meta remark: if you can, I'd say it's better to avoid this pattern of depending on .d
files, and instead aim to express sufficiently many of the dependencies ‘by hand’ directly in the makefile. Doing it this .d
way does work (ie, I'm not saying what you're doing is wrong) and appears to be labour-saving, but in my experience it tends to be a little brittle, partly because if you don't have the .d
files to hand then you suddenly have zero dependencies. In order to have the .d
files to hand, you'll have to check them in to your code repository (you are using a repository, aren't you?), but that will mean they'll frequently be trivially out of date, and... it can turn into a bit of a mess.
If one .c file includes n number of header files .We can t specify them in our make files right? It looks bit ugly. Is there any simple way to handle this?
– santosh
Nov 21 '18 at 12:11
I disagree with the discussion about auto-generated prerequisites in the last paragraph above. They are actually perfectly reliable when done correctly (unfortunately because make is a generic tool, and not a tool specifically for working with C/C++ programs, doing it right takes a bit of work). Handling prerequisites by hand is fine in simple situations but it's simply untenable in any moderate to large program. See make.mad-scientist.net/papers/… for a discussion of how to do auto-dependency correctly (even if all .d files are removed!)
– MadScientist
Nov 21 '18 at 12:35
@MadScientist thanks for the opposing point of view, and the useful link. The 'a bit of work' and the length of that page, illustrate what I regard as the downside, and why I think of this approach as 'brittle' (in my experience) rather than wrong. I've tried multiple ways of managing this, over the years, with and without automake (and I'll read your page carefully), and concluded that make is one of those systems where 'mostly correct and readable/maintainable' is better than 'completely correct but write-only'. This is probably a style/taste issue, in the end.
– Norman Gray
Nov 21 '18 at 13:23
If you have 10 files with simple prerequisites, it's fine to list things by hand. In projects I work on we have over 1500 source files and over 1700 header files across many directories (and this is nowhere near a "large" project, really). It's C++ so there is a lot of recursive header file inclusion and there is simply no way to manage that by hand. The real problem is that if you forget to add a prerequisite to your makefile then your program can break in subtle and hard to understand ways. It's not just a compile error. An unreliable makefile is often WORSE than no makefile.
– MadScientist
Nov 21 '18 at 15:10
add a comment |
As @tripleee noted in the comments, make
will by default build the first target it encounters. Since the include
files are included directly, as if they were cut-and-pasted in place, the first target in the first .d
file (which I'm guessing you'll find to be hellofunc.c
) is the first target that make
encounters, so that's what make
aims to build.
If you move the include
line to the end of the file, then the first target in the file will be hellomake
, and so that's the target make
will attempt to build by default.
Meta remark: if you can, I'd say it's better to avoid this pattern of depending on .d
files, and instead aim to express sufficiently many of the dependencies ‘by hand’ directly in the makefile. Doing it this .d
way does work (ie, I'm not saying what you're doing is wrong) and appears to be labour-saving, but in my experience it tends to be a little brittle, partly because if you don't have the .d
files to hand then you suddenly have zero dependencies. In order to have the .d
files to hand, you'll have to check them in to your code repository (you are using a repository, aren't you?), but that will mean they'll frequently be trivially out of date, and... it can turn into a bit of a mess.
If one .c file includes n number of header files .We can t specify them in our make files right? It looks bit ugly. Is there any simple way to handle this?
– santosh
Nov 21 '18 at 12:11
I disagree with the discussion about auto-generated prerequisites in the last paragraph above. They are actually perfectly reliable when done correctly (unfortunately because make is a generic tool, and not a tool specifically for working with C/C++ programs, doing it right takes a bit of work). Handling prerequisites by hand is fine in simple situations but it's simply untenable in any moderate to large program. See make.mad-scientist.net/papers/… for a discussion of how to do auto-dependency correctly (even if all .d files are removed!)
– MadScientist
Nov 21 '18 at 12:35
@MadScientist thanks for the opposing point of view, and the useful link. The 'a bit of work' and the length of that page, illustrate what I regard as the downside, and why I think of this approach as 'brittle' (in my experience) rather than wrong. I've tried multiple ways of managing this, over the years, with and without automake (and I'll read your page carefully), and concluded that make is one of those systems where 'mostly correct and readable/maintainable' is better than 'completely correct but write-only'. This is probably a style/taste issue, in the end.
– Norman Gray
Nov 21 '18 at 13:23
If you have 10 files with simple prerequisites, it's fine to list things by hand. In projects I work on we have over 1500 source files and over 1700 header files across many directories (and this is nowhere near a "large" project, really). It's C++ so there is a lot of recursive header file inclusion and there is simply no way to manage that by hand. The real problem is that if you forget to add a prerequisite to your makefile then your program can break in subtle and hard to understand ways. It's not just a compile error. An unreliable makefile is often WORSE than no makefile.
– MadScientist
Nov 21 '18 at 15:10
add a comment |
As @tripleee noted in the comments, make
will by default build the first target it encounters. Since the include
files are included directly, as if they were cut-and-pasted in place, the first target in the first .d
file (which I'm guessing you'll find to be hellofunc.c
) is the first target that make
encounters, so that's what make
aims to build.
If you move the include
line to the end of the file, then the first target in the file will be hellomake
, and so that's the target make
will attempt to build by default.
Meta remark: if you can, I'd say it's better to avoid this pattern of depending on .d
files, and instead aim to express sufficiently many of the dependencies ‘by hand’ directly in the makefile. Doing it this .d
way does work (ie, I'm not saying what you're doing is wrong) and appears to be labour-saving, but in my experience it tends to be a little brittle, partly because if you don't have the .d
files to hand then you suddenly have zero dependencies. In order to have the .d
files to hand, you'll have to check them in to your code repository (you are using a repository, aren't you?), but that will mean they'll frequently be trivially out of date, and... it can turn into a bit of a mess.
As @tripleee noted in the comments, make
will by default build the first target it encounters. Since the include
files are included directly, as if they were cut-and-pasted in place, the first target in the first .d
file (which I'm guessing you'll find to be hellofunc.c
) is the first target that make
encounters, so that's what make
aims to build.
If you move the include
line to the end of the file, then the first target in the file will be hellomake
, and so that's the target make
will attempt to build by default.
Meta remark: if you can, I'd say it's better to avoid this pattern of depending on .d
files, and instead aim to express sufficiently many of the dependencies ‘by hand’ directly in the makefile. Doing it this .d
way does work (ie, I'm not saying what you're doing is wrong) and appears to be labour-saving, but in my experience it tends to be a little brittle, partly because if you don't have the .d
files to hand then you suddenly have zero dependencies. In order to have the .d
files to hand, you'll have to check them in to your code repository (you are using a repository, aren't you?), but that will mean they'll frequently be trivially out of date, and... it can turn into a bit of a mess.
answered Nov 21 '18 at 12:04
Norman GrayNorman Gray
9,29411945
9,29411945
If one .c file includes n number of header files .We can t specify them in our make files right? It looks bit ugly. Is there any simple way to handle this?
– santosh
Nov 21 '18 at 12:11
I disagree with the discussion about auto-generated prerequisites in the last paragraph above. They are actually perfectly reliable when done correctly (unfortunately because make is a generic tool, and not a tool specifically for working with C/C++ programs, doing it right takes a bit of work). Handling prerequisites by hand is fine in simple situations but it's simply untenable in any moderate to large program. See make.mad-scientist.net/papers/… for a discussion of how to do auto-dependency correctly (even if all .d files are removed!)
– MadScientist
Nov 21 '18 at 12:35
@MadScientist thanks for the opposing point of view, and the useful link. The 'a bit of work' and the length of that page, illustrate what I regard as the downside, and why I think of this approach as 'brittle' (in my experience) rather than wrong. I've tried multiple ways of managing this, over the years, with and without automake (and I'll read your page carefully), and concluded that make is one of those systems where 'mostly correct and readable/maintainable' is better than 'completely correct but write-only'. This is probably a style/taste issue, in the end.
– Norman Gray
Nov 21 '18 at 13:23
If you have 10 files with simple prerequisites, it's fine to list things by hand. In projects I work on we have over 1500 source files and over 1700 header files across many directories (and this is nowhere near a "large" project, really). It's C++ so there is a lot of recursive header file inclusion and there is simply no way to manage that by hand. The real problem is that if you forget to add a prerequisite to your makefile then your program can break in subtle and hard to understand ways. It's not just a compile error. An unreliable makefile is often WORSE than no makefile.
– MadScientist
Nov 21 '18 at 15:10
add a comment |
If one .c file includes n number of header files .We can t specify them in our make files right? It looks bit ugly. Is there any simple way to handle this?
– santosh
Nov 21 '18 at 12:11
I disagree with the discussion about auto-generated prerequisites in the last paragraph above. They are actually perfectly reliable when done correctly (unfortunately because make is a generic tool, and not a tool specifically for working with C/C++ programs, doing it right takes a bit of work). Handling prerequisites by hand is fine in simple situations but it's simply untenable in any moderate to large program. See make.mad-scientist.net/papers/… for a discussion of how to do auto-dependency correctly (even if all .d files are removed!)
– MadScientist
Nov 21 '18 at 12:35
@MadScientist thanks for the opposing point of view, and the useful link. The 'a bit of work' and the length of that page, illustrate what I regard as the downside, and why I think of this approach as 'brittle' (in my experience) rather than wrong. I've tried multiple ways of managing this, over the years, with and without automake (and I'll read your page carefully), and concluded that make is one of those systems where 'mostly correct and readable/maintainable' is better than 'completely correct but write-only'. This is probably a style/taste issue, in the end.
– Norman Gray
Nov 21 '18 at 13:23
If you have 10 files with simple prerequisites, it's fine to list things by hand. In projects I work on we have over 1500 source files and over 1700 header files across many directories (and this is nowhere near a "large" project, really). It's C++ so there is a lot of recursive header file inclusion and there is simply no way to manage that by hand. The real problem is that if you forget to add a prerequisite to your makefile then your program can break in subtle and hard to understand ways. It's not just a compile error. An unreliable makefile is often WORSE than no makefile.
– MadScientist
Nov 21 '18 at 15:10
If one .c file includes n number of header files .We can t specify them in our make files right? It looks bit ugly. Is there any simple way to handle this?
– santosh
Nov 21 '18 at 12:11
If one .c file includes n number of header files .We can t specify them in our make files right? It looks bit ugly. Is there any simple way to handle this?
– santosh
Nov 21 '18 at 12:11
I disagree with the discussion about auto-generated prerequisites in the last paragraph above. They are actually perfectly reliable when done correctly (unfortunately because make is a generic tool, and not a tool specifically for working with C/C++ programs, doing it right takes a bit of work). Handling prerequisites by hand is fine in simple situations but it's simply untenable in any moderate to large program. See make.mad-scientist.net/papers/… for a discussion of how to do auto-dependency correctly (even if all .d files are removed!)
– MadScientist
Nov 21 '18 at 12:35
I disagree with the discussion about auto-generated prerequisites in the last paragraph above. They are actually perfectly reliable when done correctly (unfortunately because make is a generic tool, and not a tool specifically for working with C/C++ programs, doing it right takes a bit of work). Handling prerequisites by hand is fine in simple situations but it's simply untenable in any moderate to large program. See make.mad-scientist.net/papers/… for a discussion of how to do auto-dependency correctly (even if all .d files are removed!)
– MadScientist
Nov 21 '18 at 12:35
@MadScientist thanks for the opposing point of view, and the useful link. The 'a bit of work' and the length of that page, illustrate what I regard as the downside, and why I think of this approach as 'brittle' (in my experience) rather than wrong. I've tried multiple ways of managing this, over the years, with and without automake (and I'll read your page carefully), and concluded that make is one of those systems where 'mostly correct and readable/maintainable' is better than 'completely correct but write-only'. This is probably a style/taste issue, in the end.
– Norman Gray
Nov 21 '18 at 13:23
@MadScientist thanks for the opposing point of view, and the useful link. The 'a bit of work' and the length of that page, illustrate what I regard as the downside, and why I think of this approach as 'brittle' (in my experience) rather than wrong. I've tried multiple ways of managing this, over the years, with and without automake (and I'll read your page carefully), and concluded that make is one of those systems where 'mostly correct and readable/maintainable' is better than 'completely correct but write-only'. This is probably a style/taste issue, in the end.
– Norman Gray
Nov 21 '18 at 13:23
If you have 10 files with simple prerequisites, it's fine to list things by hand. In projects I work on we have over 1500 source files and over 1700 header files across many directories (and this is nowhere near a "large" project, really). It's C++ so there is a lot of recursive header file inclusion and there is simply no way to manage that by hand. The real problem is that if you forget to add a prerequisite to your makefile then your program can break in subtle and hard to understand ways. It's not just a compile error. An unreliable makefile is often WORSE than no makefile.
– MadScientist
Nov 21 '18 at 15:10
If you have 10 files with simple prerequisites, it's fine to list things by hand. In projects I work on we have over 1500 source files and over 1700 header files across many directories (and this is nowhere near a "large" project, really). It's C++ so there is a lot of recursive header file inclusion and there is simply no way to manage that by hand. The real problem is that if you forget to add a prerequisite to your makefile then your program can break in subtle and hard to understand ways. It's not just a compile error. An unreliable makefile is often WORSE than no makefile.
– MadScientist
Nov 21 '18 at 15:10
add a comment |
EDIT: considered MadScientist's comment and blog post about separate recipe for .d
files.
You could tell make how to generate the .d
files with a separate rule instead of putting this in another recipe (but see the above mentioned blog post for several reasons for not doing so).
And you should probably tell make that your default goal is hellomake
:
.DEFAULT_GOAL := hellomake
CC=gcc
CFLAGS=-I.
OBJ = hellofunc.o hellomake.o
DEPS := $(OBJ:.o=.d)
-include $(DEPS)
%.d: %.c
$(CC) $(CFLAGS) -MM -MT $@ -MF $@ $<
%.o: %.c
$(CC) -c -o $@ $< $(CFLAGS)
hellomake: hellomake.o hellofunc.o
$(CC) -o $@ $^
And it would probably be even better if you were letting make find the source files and deduce the rest:
.DEFAULT_GOAL := hellomake
CC := gcc
CFLAGS := -I.
SRCS := $(wildcard *.c)
OBJS := $(patsubst %.c,%.o,$(SRC))
DEPS := $(patsubst %.c,%.d,$(SRC))
-include $(DEPS)
%.d: %.c
$(CC) $(CFLAGS) -MM -MT $@ -MF $@ $<
%.o: %.c
$(CC) -c -o $@ $< $(CFLAGS)
hellomake: $(OBJS)
$(CC) -o $@ $^
Finally, following MadScientist's advices, a better, more efficient, less prone to failures solution could be:
.DEFAULT_GOAL := hellomake
CC := gcc
CFLAGS := -I.
SRCS := $(wildcard *.c)
OBJS := $(patsubst %.c,%.o,$(SRC))
DEPS := $(wildcard $(patsubst %.c,%.d,$(SRC)))
include $(DEPS)
%.o: %.c %.d
$(CC) -MT $@ -MMD -MP -MF $*.Td $(CFLAGS) -c -o $@ $<
mv -f $*.Td $*.d && touch $@
hellomake: $(OBJS)
$(CC) -o $@ $^
%.d: ;
.PRECIOUS: %.d
Ohh Got it. Thanks! Do we have any tutorials or articles for "-MM -MT" dependency options ? Can you please share if any ?
– santosh
Nov 21 '18 at 12:36
2
Actually creating a separate recipe for.d
files leads to a lot of unpleasant side-effects. The new modern (and best) method for creating prerequisite files is to create them as part of building the object file, not in a separate rule. See the blog post I lined to in comments above for a full discussion.
– MadScientist
Nov 21 '18 at 12:37
BTW, It didnt worked. I copied same make file content above. Still its comping only one .c file.
– santosh
Nov 21 '18 at 13:13
@santosh: are you sure both files include this header file? And did you check the content of the.d
files to verify that this header file is really listed as a dependency?
– Renaud Pacalet
Nov 21 '18 at 13:24
Yeah, I verified. I am including header file in both .c files. And .d files also has header file listed in it.
– santosh
Nov 21 '18 at 13:38
|
show 2 more comments
EDIT: considered MadScientist's comment and blog post about separate recipe for .d
files.
You could tell make how to generate the .d
files with a separate rule instead of putting this in another recipe (but see the above mentioned blog post for several reasons for not doing so).
And you should probably tell make that your default goal is hellomake
:
.DEFAULT_GOAL := hellomake
CC=gcc
CFLAGS=-I.
OBJ = hellofunc.o hellomake.o
DEPS := $(OBJ:.o=.d)
-include $(DEPS)
%.d: %.c
$(CC) $(CFLAGS) -MM -MT $@ -MF $@ $<
%.o: %.c
$(CC) -c -o $@ $< $(CFLAGS)
hellomake: hellomake.o hellofunc.o
$(CC) -o $@ $^
And it would probably be even better if you were letting make find the source files and deduce the rest:
.DEFAULT_GOAL := hellomake
CC := gcc
CFLAGS := -I.
SRCS := $(wildcard *.c)
OBJS := $(patsubst %.c,%.o,$(SRC))
DEPS := $(patsubst %.c,%.d,$(SRC))
-include $(DEPS)
%.d: %.c
$(CC) $(CFLAGS) -MM -MT $@ -MF $@ $<
%.o: %.c
$(CC) -c -o $@ $< $(CFLAGS)
hellomake: $(OBJS)
$(CC) -o $@ $^
Finally, following MadScientist's advices, a better, more efficient, less prone to failures solution could be:
.DEFAULT_GOAL := hellomake
CC := gcc
CFLAGS := -I.
SRCS := $(wildcard *.c)
OBJS := $(patsubst %.c,%.o,$(SRC))
DEPS := $(wildcard $(patsubst %.c,%.d,$(SRC)))
include $(DEPS)
%.o: %.c %.d
$(CC) -MT $@ -MMD -MP -MF $*.Td $(CFLAGS) -c -o $@ $<
mv -f $*.Td $*.d && touch $@
hellomake: $(OBJS)
$(CC) -o $@ $^
%.d: ;
.PRECIOUS: %.d
Ohh Got it. Thanks! Do we have any tutorials or articles for "-MM -MT" dependency options ? Can you please share if any ?
– santosh
Nov 21 '18 at 12:36
2
Actually creating a separate recipe for.d
files leads to a lot of unpleasant side-effects. The new modern (and best) method for creating prerequisite files is to create them as part of building the object file, not in a separate rule. See the blog post I lined to in comments above for a full discussion.
– MadScientist
Nov 21 '18 at 12:37
BTW, It didnt worked. I copied same make file content above. Still its comping only one .c file.
– santosh
Nov 21 '18 at 13:13
@santosh: are you sure both files include this header file? And did you check the content of the.d
files to verify that this header file is really listed as a dependency?
– Renaud Pacalet
Nov 21 '18 at 13:24
Yeah, I verified. I am including header file in both .c files. And .d files also has header file listed in it.
– santosh
Nov 21 '18 at 13:38
|
show 2 more comments
EDIT: considered MadScientist's comment and blog post about separate recipe for .d
files.
You could tell make how to generate the .d
files with a separate rule instead of putting this in another recipe (but see the above mentioned blog post for several reasons for not doing so).
And you should probably tell make that your default goal is hellomake
:
.DEFAULT_GOAL := hellomake
CC=gcc
CFLAGS=-I.
OBJ = hellofunc.o hellomake.o
DEPS := $(OBJ:.o=.d)
-include $(DEPS)
%.d: %.c
$(CC) $(CFLAGS) -MM -MT $@ -MF $@ $<
%.o: %.c
$(CC) -c -o $@ $< $(CFLAGS)
hellomake: hellomake.o hellofunc.o
$(CC) -o $@ $^
And it would probably be even better if you were letting make find the source files and deduce the rest:
.DEFAULT_GOAL := hellomake
CC := gcc
CFLAGS := -I.
SRCS := $(wildcard *.c)
OBJS := $(patsubst %.c,%.o,$(SRC))
DEPS := $(patsubst %.c,%.d,$(SRC))
-include $(DEPS)
%.d: %.c
$(CC) $(CFLAGS) -MM -MT $@ -MF $@ $<
%.o: %.c
$(CC) -c -o $@ $< $(CFLAGS)
hellomake: $(OBJS)
$(CC) -o $@ $^
Finally, following MadScientist's advices, a better, more efficient, less prone to failures solution could be:
.DEFAULT_GOAL := hellomake
CC := gcc
CFLAGS := -I.
SRCS := $(wildcard *.c)
OBJS := $(patsubst %.c,%.o,$(SRC))
DEPS := $(wildcard $(patsubst %.c,%.d,$(SRC)))
include $(DEPS)
%.o: %.c %.d
$(CC) -MT $@ -MMD -MP -MF $*.Td $(CFLAGS) -c -o $@ $<
mv -f $*.Td $*.d && touch $@
hellomake: $(OBJS)
$(CC) -o $@ $^
%.d: ;
.PRECIOUS: %.d
EDIT: considered MadScientist's comment and blog post about separate recipe for .d
files.
You could tell make how to generate the .d
files with a separate rule instead of putting this in another recipe (but see the above mentioned blog post for several reasons for not doing so).
And you should probably tell make that your default goal is hellomake
:
.DEFAULT_GOAL := hellomake
CC=gcc
CFLAGS=-I.
OBJ = hellofunc.o hellomake.o
DEPS := $(OBJ:.o=.d)
-include $(DEPS)
%.d: %.c
$(CC) $(CFLAGS) -MM -MT $@ -MF $@ $<
%.o: %.c
$(CC) -c -o $@ $< $(CFLAGS)
hellomake: hellomake.o hellofunc.o
$(CC) -o $@ $^
And it would probably be even better if you were letting make find the source files and deduce the rest:
.DEFAULT_GOAL := hellomake
CC := gcc
CFLAGS := -I.
SRCS := $(wildcard *.c)
OBJS := $(patsubst %.c,%.o,$(SRC))
DEPS := $(patsubst %.c,%.d,$(SRC))
-include $(DEPS)
%.d: %.c
$(CC) $(CFLAGS) -MM -MT $@ -MF $@ $<
%.o: %.c
$(CC) -c -o $@ $< $(CFLAGS)
hellomake: $(OBJS)
$(CC) -o $@ $^
Finally, following MadScientist's advices, a better, more efficient, less prone to failures solution could be:
.DEFAULT_GOAL := hellomake
CC := gcc
CFLAGS := -I.
SRCS := $(wildcard *.c)
OBJS := $(patsubst %.c,%.o,$(SRC))
DEPS := $(wildcard $(patsubst %.c,%.d,$(SRC)))
include $(DEPS)
%.o: %.c %.d
$(CC) -MT $@ -MMD -MP -MF $*.Td $(CFLAGS) -c -o $@ $<
mv -f $*.Td $*.d && touch $@
hellomake: $(OBJS)
$(CC) -o $@ $^
%.d: ;
.PRECIOUS: %.d
edited Nov 21 '18 at 14:43
answered Nov 21 '18 at 12:22
Renaud PacaletRenaud Pacalet
9,49821730
9,49821730
Ohh Got it. Thanks! Do we have any tutorials or articles for "-MM -MT" dependency options ? Can you please share if any ?
– santosh
Nov 21 '18 at 12:36
2
Actually creating a separate recipe for.d
files leads to a lot of unpleasant side-effects. The new modern (and best) method for creating prerequisite files is to create them as part of building the object file, not in a separate rule. See the blog post I lined to in comments above for a full discussion.
– MadScientist
Nov 21 '18 at 12:37
BTW, It didnt worked. I copied same make file content above. Still its comping only one .c file.
– santosh
Nov 21 '18 at 13:13
@santosh: are you sure both files include this header file? And did you check the content of the.d
files to verify that this header file is really listed as a dependency?
– Renaud Pacalet
Nov 21 '18 at 13:24
Yeah, I verified. I am including header file in both .c files. And .d files also has header file listed in it.
– santosh
Nov 21 '18 at 13:38
|
show 2 more comments
Ohh Got it. Thanks! Do we have any tutorials or articles for "-MM -MT" dependency options ? Can you please share if any ?
– santosh
Nov 21 '18 at 12:36
2
Actually creating a separate recipe for.d
files leads to a lot of unpleasant side-effects. The new modern (and best) method for creating prerequisite files is to create them as part of building the object file, not in a separate rule. See the blog post I lined to in comments above for a full discussion.
– MadScientist
Nov 21 '18 at 12:37
BTW, It didnt worked. I copied same make file content above. Still its comping only one .c file.
– santosh
Nov 21 '18 at 13:13
@santosh: are you sure both files include this header file? And did you check the content of the.d
files to verify that this header file is really listed as a dependency?
– Renaud Pacalet
Nov 21 '18 at 13:24
Yeah, I verified. I am including header file in both .c files. And .d files also has header file listed in it.
– santosh
Nov 21 '18 at 13:38
Ohh Got it. Thanks! Do we have any tutorials or articles for "-MM -MT" dependency options ? Can you please share if any ?
– santosh
Nov 21 '18 at 12:36
Ohh Got it. Thanks! Do we have any tutorials or articles for "-MM -MT" dependency options ? Can you please share if any ?
– santosh
Nov 21 '18 at 12:36
2
2
Actually creating a separate recipe for
.d
files leads to a lot of unpleasant side-effects. The new modern (and best) method for creating prerequisite files is to create them as part of building the object file, not in a separate rule. See the blog post I lined to in comments above for a full discussion.– MadScientist
Nov 21 '18 at 12:37
Actually creating a separate recipe for
.d
files leads to a lot of unpleasant side-effects. The new modern (and best) method for creating prerequisite files is to create them as part of building the object file, not in a separate rule. See the blog post I lined to in comments above for a full discussion.– MadScientist
Nov 21 '18 at 12:37
BTW, It didnt worked. I copied same make file content above. Still its comping only one .c file.
– santosh
Nov 21 '18 at 13:13
BTW, It didnt worked. I copied same make file content above. Still its comping only one .c file.
– santosh
Nov 21 '18 at 13:13
@santosh: are you sure both files include this header file? And did you check the content of the
.d
files to verify that this header file is really listed as a dependency?– Renaud Pacalet
Nov 21 '18 at 13:24
@santosh: are you sure both files include this header file? And did you check the content of the
.d
files to verify that this header file is really listed as a dependency?– Renaud Pacalet
Nov 21 '18 at 13:24
Yeah, I verified. I am including header file in both .c files. And .d files also has header file listed in it.
– santosh
Nov 21 '18 at 13:38
Yeah, I verified. I am including header file in both .c files. And .d files also has header file listed in it.
– santosh
Nov 21 '18 at 13:38
|
show 2 more comments
You have not declared any dependency on
hellomake.h
so of course Make ignores it.– tripleee
Nov 21 '18 at 11:32
@tripleee, Can you please give brief answer by updating my make file? I am new to make
– santosh
Nov 21 '18 at 11:39
I am including both hellomake.d , hellofunc.d files using include directive.. That should work right?
– santosh
Nov 21 '18 at 11:42
I think this question should not have been marked as duplicate of a the question cited by those who voted to close. This one makes use of automatic dependency generation. Manually adding header files to the prerequisites should not be needed.
– Renaud Pacalet
Nov 21 '18 at 14:40