Search for "Recursive Make Considered Harmful". That contains examples of how you make make really work. This is a rule that's useful to put in all your makefiles: %.show: @echo "$* = $($*)" So whenever you're not sure what a variable in the makefile is getting set to, you can do "make FOO.show" and it will show you the value of $(FOO). This helps a lot with debugging. The other thing is to produce dependency files which work; the recursive make paper above explains this. Then you write generator rules and everything else will just fall into place. Don't be scared of creating new extensions for things, so that you can use them to trigger off other rules. If people whinge, you can always delete the intermediate files when they're done. But, for example, I build yacc and lex scripts into .C_ and .H_ files. I then have a rule which will turn .C_ into a .o by compiling it; hence .C_ means "machine generated C++". The reason for the intermediate stage is that you can't just write generic generator rules for .C because it'll moan that it can't work out how to check other (human written) .C are up to date - so you need to differentiate the node types. Essentially there are three species in well formed make ecologies. Leaf nodes, which are always human edited. Branch nodes which a) depend on leaf nodes or branch nodes and b) are ALWAYS machine generated. Links; which are sets of rules to compile a number of child nodes into a parent node. Note that it is no problem that the graph of these contains cycles - however containing a loop is an error. Most make problems are caused by: 1) Believing there are only two species, nodes and links. 2) Failing to understand the way % rules are matched. Read the guide carefully. 3) Failing to "debug" the makefile in the same way as you would debug other code. Too many people don't speak the language so they're as stuck debugging it as they would be debugging any other programming system they don't speak. 4) Failing to generate dependencies properly; without telling the system where the links are, it cannot possibly work out how to build things properly. When in doubt OVERGENERATE dependencies. Otherwise you will end up not building things that you should.