# GNU make syntax reigns in this file.
all_cflags += -Werror
all_cppflags += -MD -MP -MF .deps/$(subst .._,,$(subst /,_,$(subst $(srcdir)/,,$<))).d -MQ $@
all_cxxflags += -Werror
A2X = a2x
ASCIIDOC = asciidoc
CLANG_FORMAT = clang-format
CLANG_TIDY = clang-tidy
COMPILEDB = compiledb
CPPCHECK = cppcheck
CPPCHECK_SUPPRESSIONS = misc/cppcheck-suppressions.txt
DOCKER = docker
SCAN_BUILD = scan-build
SHELLCHECK = shellcheck
SHELLCHECK_EXCLUDES = misc/shellcheck-excludes.txt
TEST = test
version := \
$(shell (git --git-dir=$(srcdir)/.git describe --dirty || git --git-dir=$(srcdir)/.git describe || echo vunknown) \
2>/dev/null | sed -e 's/v//' -e 's/-/+/' -e 's/-/_/g')
dist_dir = ccache-$(version)
dist_archives = \
ccache-$(version).tar.gz \
ccache-$(version).tar.xz
generated_docs = \
LICENSE.html \
doc/AUTHORS.html \
doc/MANUAL.html \
doc/NEWS.html \
doc/ccache.1
built_dist_files = $(generated_sources) $(generated_docs)
non_third_party_headers_without_cpp = \
src/Checksum.hpp \
src/File.hpp \
src/FormatNonstdStringView.hpp \
src/NonCopyable.hpp \
src/NullCompressor.hpp \
src/NullDecompressor.hpp \
src/ProgressBar.hpp \
src/ScopeGuard.hpp \
src/Stat.hpp \
src/StdMakeUnique.hpp \
src/ThreadPool.hpp \
src/exceptions.hpp \
src/macroskip.hpp \
src/system.hpp \
unittest/framework.hpp \
unittest/util.hpp
non_third_party_headers = $(subst .cpp,.hpp,$(non_third_party_sources)) \
$(non_third_party_headers_without_cpp)
third_party_headers = \
src/third_party/catch.hpp \
src/third_party/fmt/core.h \
src/third_party/fmt/format-inl.h \
src/third_party/fmt/format.h \
src/third_party/getopt_long.h \
src/third_party/minitrace.h \
src/third_party/nonstd/optional.hpp \
src/third_party/nonstd/string_view.hpp \
src/third_party/xxhash.h
headers = $(non_third_party_headers) $(third_party_headers)
files_to_clean += *.tar.gz *.tar.xz *.xml doc/*.xml .deps/* perfdir.*
files_to_clean += compile_commands.json
files_to_distclean += $(built_dist_files) src/version.cpp
files_to_distclean += .deps dev.mk
source_dist_files = \
$(non_third_party_sources) \
$(third_party_sources) \
$(headers) \
$(test_sources) \
CONTRIBUTING.md \
GPL-3.0.txt \
LICENSE.adoc \
Makefile.in \
README.md \
autogen.sh \
config.guess \
config.h.in \
config.sub \
configure \
configure.ac \
dev.mk.in \
doc/AUTHORS.adoc \
doc/MANUAL.adoc \
doc/NEWS.adoc \
install-sh \
m4 \
src/main.cpp \
src/third_party/minitrace.c \
test/run \
test/suites/*.bash \
unittest/catch2_tests.cpp \
unittest/catch2_tests.hpp
dist_files = \
$(addprefix $(srcdir)/, $(source_dist_files)) \
$(built_dist_files)
ifneq ($(shell sed 's/.*"\(.*\)".*/\1/' src/version.cpp 2>/dev/null),$(version))
$(shell echo 'extern const char CCACHE_VERSION[]; const char CCACHE_VERSION[] = "$(version)";' >src/version.cpp)
endif
src/version.o: src/version.cpp
.PHONY: dist
dist: $(dist_archives)
$(dist_archives): $(dist_files)
tmpdir=$$(mktemp -d /tmp/tmp-ccache-dist.XXXXXX) && \
dir=$$tmpdir/$(dist_dir) && \
mkdir $$dir && \
(cd $(srcdir) && \
rsync -r --relative $(source_dist_files) $$dir) && \
cp $(srcdir)/doc/INSTALL-from-release-archive.md $$dir/INSTALL.md && \
(cd $(builddir) && \
rsync -r --relative $(built_dist_files) $$dir) && \
echo "Remove this file to enable developer mode." >$$dir/dev_mode_disabled && \
(cd $$tmpdir && \
tarcompression= && \
case $@ in \
*.gz) tarcompression=-z ;; \
*.xz) tarcompression=-J ;; \
esac && \
tar -c $$tarcompression -f $(CURDIR)/$@ $(dist_dir)) && \
rm -rf $$tmpdir
# $(1): extra configure options
define do_distcheck
tmpdir=$$(mktemp -d /tmp/tmp-ccache-distcheck.XXXXXX) && \
(cd $$tmpdir && \
tar xf $(CURDIR)/$< && \
mkdir -p $(dist_dir)/build && \
chmod -R a-w $(dist_dir) && \
chmod u+w $(dist_dir)/build && \
cd $(dist_dir)/build && \
../configure --enable-more-warnings --prefix=$$tmpdir/root --sysconfdir=/etc $(1) && \
$(MAKE) install V=1 && \
$(MAKE) installcheck V=1) && \
chmod -R u+w $$tmpdir/$(dist_dir) && \
rm -rf $$tmpdir
endef
.PHONY: distcheck
distcheck: $(firstword $(dist_archives))
$(call do_distcheck, CFLAGS=-Werror CXXFLAGS=-Werror)
$(call do_distcheck, --with-libzstd-from-internet --with-libb2-from-internet)
$(call do_distcheck, CC=clang CXX=clang++)
.PHONY: docs
docs: $(generated_docs)
%.html: %.adoc
@mkdir -p $(@D)
$(if $(quiet),@echo " ASCIIDOC $@")
$(Q)$(ASCIIDOC) -o $@ -a revnumber=$(version) -a toc -b xhtml11 $<
%.xml: %.adoc
@mkdir -p $(@D)
# Make literals stand out as bold in the man page:
$(if $(quiet),@echo " ASCIIDOC $@")
$(Q)$(ASCIIDOC) -a revnumber=$(version) -d manpage -b docbook -o - $< | \
perl -pe 's!(.*?)!\1!g' >$@
doc/ccache.1: doc/MANUAL.xml
$(if $(quiet),@echo " A2X $@")
$(Q)$(A2X) --doctype manpage --format manpage $<
.PHONY: update-authors
update-authors:
git log --pretty=format:"%H %aN%n%(trailers:only)" \
| grep -Ev 'd7c5056beda5483fcd5c098165fffd9be86fe98d|http|Conflicts:' \
| grep '^[^ ]' \
| sed -r -e 's/[^ ]+/*/' -e 's/<.*//' -e 's/ *$$//' \
| sort -u \
| perl -00 -p -i -e 's/^\*.*/ . "\n"/es' doc/AUTHORS.adoc
.PHONY: check-syntax
check-syntax:
$(CC) $(all_cppflags) -I. $(all_cxxflags) -S -o /dev/null $(CHK_SOURCES)
.PHONY: cppcheck
cppcheck:
$(CPPCHECK) --suppressions-list=$(CPPCHECK_SUPPRESSIONS) \
--inline-suppr -q --enable=all --force -I . \
--template='cppcheck: warning: {id}:{file}:{line}: {message}' \
$(non_third_party_sources) src/main.cpp $(test_sources)
.PHONY: shellcheck
shellcheck: test/suites/*.bash
$(SHELLCHECK) --shell=bash --exclude=$(shell sed -e 's/:.*//' <$(SHELLCHECK_EXCLUDES) | grep -v '#' | tr '\n' ',' | sed -e 's/,$$//') $^
.PHONY: format
format:
$(CLANG_FORMAT) -i $(non_third_party_headers) $(non_third_party_sources) $(test_sources)
# pip install compiledb
compile_commands.json:
$(COMPILEDB) -n $(MAKE) all unittest
.PHONY: tidy
tidy: compile_commands.json
$(CLANG_TIDY) $(all_sources)
.PHONY: analyze
analyze:
$(SCAN_BUILD) --use-cc="$(CC)" --use-c++="$(CXX)" $(srcdir)/configure
$(SCAN_BUILD) --use-cc="$(CC)" --use-c++="$(CXX)" --status-bugs $(MAKE) -B
BUILDENV = ubuntu
DOCKER_IMAGE_TAG = ccache/build:$(BUILDENV)
.PHONY: docker
docker: buildenv/$(BUILDENV)/Dockerfile
$(DOCKER) inspect $(DOCKER_IMAGE_TAG) >/dev/null || $(DOCKER) build -t $(DOCKER_IMAGE_TAG) buildenv/$(BUILDENV)
$(DOCKER) run --rm -v $(PWD):/build -w /build $(DOCKER_IMAGE_TAG) misc/build.sh $(TEST)
.PHONY: travis
travis: .travis/Dockerfile
$(DOCKER) inspect travis-build >/dev/null || $(DOCKER) build -t travis-build .travis
$(DOCKER) run --rm --volume $(PWD):/src --tmpfs /dst:rw,exec --env ASAN_OPTIONS='$(ASAN_OPTIONS)' travis-build \
sh -c "cd /src && ./autogen.sh && cd /dst && CC=$(CC) CFLAGS='$(CFLAGS)' CXX=$(CXX) CXXFLAGS='$(CXXFLAGS)' LDFLAGS='$(LDFLAGS)' /src/configure $(CONFIGURE) && CC=$(CC) CFLAGS='$(CFLAGS)' make V=$(V) && CC=$(CC) make V=$(V) $(TEST)"
-include .deps/*.d