The Super-Makefile
May 4, 2009 at 8:36 pm | In coding | Leave a CommentTags: c, coding, makefile
After toying with build systems off and on for months, I concluded today that make is about as advanced as I ever need to get for my projects. In the past, I recall using this gem of a Makefile. But my needs in a build process have grown a little. First of all, I now prefer C to C++, so that had to be changed. Then I had to go about adding static and shared library abilities to it. Then I added “clean” and “distclean” build targets, and include and library search paths got introduced somewhere along the way.
After good half hour of modification, I had the following Makefile, posted here mainly so I can find it easily from any computer. By modifying the first six variables defined in the Makefile, it can be adapted to almost any C project of reasonable complexity. It has no support for cross-platform library identification, out-of-source builds, or debug and release build toggles. But on the other hand, I can never get those things to work right any way.
Toggling between static library, shared library, and executable build modes is performed by setting the LIBRARY variable to “static”, “shared”, or anything that isn’t those two values.
PROJECT=foo SOURCES=bar.c baz.c LIBRARY=nope INCPATHS=../some_other_project/ LIBPATHS=../yet_another_project/ LDFLAGS=-ldosomething CFLAGS=-c -Wall CC=gcc # ------------ MAGIC BEGINS HERE ------------- # Automatic generation of some important lists OBJECTS=$(SOURCES:.c=.o) INCFLAGS=$(foreach TMP,$(INCPATHS),-I$(TMP)) LIBFLAGS=$(foreach TMP,$(LIBPATHS),-L$(TMP)) # Set up the output file names for the different output types ifeq "$(LIBRARY)" "shared" BINARY=lib$(PROJECT).so LDFLAGS += -shared else ifeq "$(LIBRARY)" "static" BINARY=lib$(PROJECT).a else BINARY=$(PROJECT) endif all: $(SOURCES) $(BINARY) $(BINARY): $(OBJECTS) # Link the object files, or archive into a static library ifeq "$(LIBRARY)" "static" ar rcs $(BINARY) $(OBJECTS) else $(CC) $(LIBFLAGS) $(OBJECTS) $(LDFLAGS) -o $@ endif .c.o: $(CC) $(INCFLAGS) $(CFLAGS) -fPIC $< -o $@ distclean: clean rm -f $(BINARY) clean: rm -f $(OBJECTS)
No Comments Yet »
RSS feed for comments on this post. TrackBack URI
Leave a comment
Blog at WordPress.com. | Theme: Pool by Borja Fernandez.
Entries and comments feeds.