Makefile

Posted on July 1, 2014
Tags: c

1 Makefile

Makefile build rule looks like stuff.o: stuff.c stuff.h
which tells us we can only build [left-hand side]stuff.o, only if we find [right-hand side] files stuff.c stuff.h

# CC is our chosen compiler gcc / g++ / llvmcc
CC=gcc
#`-I somedirectory` flag adds directories to be searched for include files 
INCDIRS=-I.
#`-O0` flag is OPTIMIZATION flag, we use `-O0` for minimal optimization, `-O3` for max optimization
OPT=-O0
#CFLAGS just brings it(the flags defined above) all together 
CFLAGS=-Wall -Wextra -g $(INCDIRS) $(OPT)

#CFILES are your input c files
CFILES=x.c y.c 
#OBJECTS are your output object file after using gcc or g++ on your CFILES
OBJECTS=x.o y.o 

#B
BINARY=bin

all: $(BINARY)

$(BINARY): $(OBJECTS)
		$(CC) -o $@ $^

# %.o is a wildcard for .o object files , same for %.c
# building any object .o file depends on it's respective .c file
# `$@` means whatever is on the left-hand side of the build rule colon which is %.o in this case 
# `$^` means whatever is on the right-hand side of the build rule colon which is %.c in this case
%.o: %.c
		$(CC) $(CFLAGS) -c -o $@ $^

clean:
		rm -rf $(BINARY) $(OBJECTS)

2 Lean Makefile

filepaths * $(addsuffix .c,foo bar) returns foo.c bar.c * $(addprefix $(OUT)/testcpp/,$(CPP_SRCS:.cpp=.o)) returns path appended object, home/testcpp/myfuns.o *$(CPP_SRCS:.cpp=.o) replaces extension .cpp with .o
CPP_SRCS is myfuncs.cpp meaning this replaces myfuncs.cpp to myfuncs.o

# tells us $(CXX) means g++ compiler
CXX ?= c++
# -O3 is a g++ flag for code optimization
CPPFLAGS = -O3
# first make the lean.mk makefile
include lean.mk


CPP_SRCS = myfuns.cpp
CPP_OBJS = $(addprefix $(OUT)/testcpp/,$(CPP_SRCS:.cpp=.o))
 

all: run_test run_interp

$(OUT)/testcpp/%.o: %.cpp
	@mkdir -p "$(@D)"
	$(CXX) -std=c++14 -c -o $@ $< $(CPPFLAGS) `leanc --print-cflags`
   #g++    -std=c++14 -c -o something/testcpp/myfuns.o myfunc.cpp -O3 `leanc --print-cflags`

# $< refers to %.cpp
# $@ refers to $(OUT)/testcpp/%.o


# to avoid conflicts between the system C++ stdlib needed by the above object file and the internal one used in the Lean runtime,
# we need to dynamically link the Lean runtime.

ifeq ($(OS),Windows_NT)
# make S.so find testcpp.so
  export PATH := $(BIN_OUT):$(PATH)
else
# find libleanshared.so
  TEST_SHARED_LINK_FLAGS := -Wl,-rpath,`lean --print-prefix`/lib/lean
endif

$(BIN_OUT)/testcpp.so: $(CPP_OBJS) | $(BIN_OUT)
	$(CXX) -shared -o $@ $^ `leanc -shared --print-ldflags`
   # g++ -shared -o $(BIN_OUT)/testcpp.so $(CPP_OBJS) `leanc -shared --print-ldflags`

$(BIN_OUT)/test: $(LIB_OUT)/libMain.a $(CPP_OBJS) | $(BIN_OUT)
	$(CXX) -o $@ $^ `leanc -shared --print-ldflags` -lleanshared $(TEST_SHARED_LINK_FLAGS)

run_test: $(BIN_OUT)/test
	$^

# also test interpreter; see doc/dev/ffi.md
$(BIN_OUT)/S.so: $(C_OUT)/Main/S.c $(BIN_OUT)/testcpp.so
	leanc -shared -o $@ $^

run_interp: $(BIN_OUT)/S.so
	lean --load-dynlib=$^ --run Main.lean
out: a.req b.req c.req
	cat a.req b.req c.req > out

%.req: %.in
	cp $< $@
	echo Bleh >> $@

result is shown below

cp a.in a.req
echo Bleh >> a.req
cp b.in b.req
echo Bleh >> b.req
cp c.in c.req
echo Bleh >> c.req

cat a.req b.req c.req > out