star-mc

Parallel estimation of Monte Carlo integrators
git clone git://git.meso-star.fr/star-mc.git
Log | Files | Refs | README | LICENSE

commit ddfc5b02224b0bdd3a86e7918a05b4d7f6312232
parent 45205f13155946ff366ca178842b4919a85290a0
Author: Vincent Forest <vincent.forest@meso-star.com>
Date:   Fri, 19 May 2023 18:27:20 +0200

Extensive rework of the POSIX Makefile

Rewrite the way the "test_smc_light_path" test is handled. This test can
only be compiled and executed if the Star-3D dependency is found.
Previously, this condition was not properly checked, resulting in
compilation errors when Star-3D was not found.

Split the linker flags in 2 different macros: the SOFLAGS macro defines
the flags when creating a shared object, i.e. a dynamic library, and the
LDFLAGS macro defines the linker options for all linking operations,
i.e. when creating a shared object or an executable.

Add the BUILD_TYPE macro which controls if the compilation is done in
RELEASE or in DEBUG: the CFLAGS and LDFLAGS macros are defined according
to BUILD_TYPE.

Add building the library as a static library. The new LIB_TYPE macro
controls whether the generated library is a shared object or an archive,
depending on whether its value is SHARED or STATIC respectively. Note
that the new macro PCFLAGS, whose value depends on LIB_TYPE, controls
whether pkg-config fetches dependencies for static linking or not.

Do not hide the compiler commands anymore (except for the file
dependency check). There is no particular advantage in doing this and it
is sane to see the compiler options used. In the same spirit, the
commands executed by the clean, distclean and lint targets are also
displayed to show what they do.

Use the new install function in the make.sh script to install the files.
It creates the target directory if necessary and copies the files only
if they are updated, thus avoiding forcing the reconstruction for
projects relying on the library after copying its unchanged header
files.

Clean up the make by replacing the sed directives with basename, which
is what these seds were actually doing. We also removed an unnecessary
input argument check in the config_test function since it is only called
internally and should be called correctly, except for a bug. We redirect
error messages from the for loop into the run_test function to show only
the defined error message and no longer show the number of failed tests
as it seems unnecessary.

Diffstat:
M.gitignore | 1+
MMakefile | 145++++++++++++++++++++++++++++++++++++++++++++++---------------------------------
Mconfig.mk | 64+++++++++++++++++++++++++++++++++++++++++++++++-----------------
Mmake.sh | 60++++++++++++++++++++++++++----------------------------------
4 files changed, 159 insertions(+), 111 deletions(-)

diff --git a/.gitignore b/.gitignore @@ -10,4 +10,5 @@ test* .test tags smc.pc +smc-local.pc image.ppm diff --git a/Makefile b/Makefile @@ -34,6 +34,10 @@ include config.mk +LIBNAME_STATIC = libsmc.a +LIBNAME_SHARED = libsmc.so +LIBNAME = $(LIBNAME_$(LIB_TYPE)) + ################################################################################ # Star-MC building ################################################################################ @@ -42,67 +46,75 @@ SRC =\ src/smc_doubleN.c\ src/smc_estimator.c\ src/smc_type.c - OBJ = $(SRC:.c=.o) DEP = $(SRC:.c=.d) build_library: .config $(DEP) - @$(MAKE) -fMakefile $$(for i in $(DEP); do echo -f $${i}; done) libsmc.so + @$(MAKE) -fMakefile $$(for i in $(DEP); do echo -f $${i}; done)\ + $$(if [ -n "$(LIBNAME)" ]; then\ + echo "$(LIBNAME)";\ + else\ + echo "$(LIBNAME_SHARED)";\ + fi) $(OBJ): config.mk -libsmc.so: $(OBJ) - @echo "LD $@" - @$(CC) $(CFLAGS) $(LIBS) -fopenmp -o $@ $(OBJ) $(LDFLAGS) +$(LIBNAME_SHARED): $(OBJ) + $(CC) $(CFLAGS) $(DPDC_CFLAGS) -fopenmp -o $@ $(OBJ) $(LDFLAGS) $(SOFLAGS) $(DPDC_LIBS) + +$(LIBNAME_STATIC): $(OBJ) + $(AR) -rc $@ $? + $(RANLIB) $@ .config: config.mk @echo "Find packages"; rm -f $@ - @$(PKG_CONFIG) --atleast-version $(RSYS_VERSION) rsys \ - || (echo "RSys $(RSYS_VERSION) not found" >&2; exit 1) - @$(PKG_CONFIG) --atleast-version $(STAR-SP_VERSION) star-sp \ - || (echo "Star-SP $(STAR-SP_VERSION) not found" >&2; exit 1) - @$(PKG_CONFIG) --atleast-version $(STAR-3D_VERSION) s3d \ - || echo "Star-3D $(STAR-3D_VERSION) not found" >&2 # Not required + @if ! $(PKG_CONFIG) --atleast-version $(RSYS_VERSION) rsys; then\ + echo "rsys $(RSYS_VERSION) not found" >&2; exit 1; fi + @if ! $(PKG_CONFIG) --atleast-version $(STAR-SP_VERSION) star-sp; then\ + echo "star-sp $(STAR-SP_VERSION) not found" >&2; exit 1; fi @echo "config done" > $@ .SUFFIXES: .c .d .o .c.d: - @echo "DEP $@" - @$(CC) $(CFLAGS) -MM -MT "$(@:.d=.o) $@" $< -MF $@ + @$(CC) $(CFLAGS) $(DPDC_CFLAGS) -fopenmp -MM -MT "$(@:.d=.o) $@" $< -MF $@ .c.o: - @echo "CC $@" - @$(CC) $(CFLAGS) $(INCS) -fopenmp -DSMC_SHARED_BUILD -c $< -o $@ + $(CC) $(CFLAGS) $(DPDC_CFLAGS) -fopenmp -DSMC_SHARED_BUILD -c $< -o $@ ################################################################################ # Installation ################################################################################ pkg: @echo "Setup smc.pc" - @sed -e 's#@PREFIX@#$(PREFIX)#g' \ - -e 's#@VERSION@#$(VERSION)#g' \ - -e 's#@RSYS_VERSION@#$(RSYS_VERSION)#g' \ - -e 's#@STAR-3D_VERSION@#$(STAR-3D_VERSION)#g' \ - -e 's#@STAR-SP_VERSION@#$(STAR-SP_VERSION)#g' \ + @sed -e 's#@PREFIX@#$(PREFIX)#g'\ + -e 's#@VERSION@#$(VERSION)#g'\ + -e 's#@RSYS_VERSION@#$(RSYS_VERSION)#g'\ + -e 's#@STAR-SP_VERSION@#$(STAR-SP_VERSION)#g'\ smc.pc.in > smc.pc +smc-local.pc: smc.pc.in + @sed -e '1d'\ + -e 's#^includedir=.*#includedir=./src/#'\ + -e 's#^libdir=.*#libdir=./#'\ + -e 's#@VERSION@#$(VERSION)#g'\ + -e 's#@RSYS_VERSION@#$(RSYS_VERSION)#g'\ + -e 's#@STAR-SP_VERSION@#$(STAR-SP_VERSION)#g'\ + smc.pc.in > $@ + install: build_library pkg - mkdir -p $(DESTDIR)$(PREFIX)/lib - mkdir -p $(DESTDIR)$(PREFIX)/lib/pkgconfig - mkdir -p $(DESTDIR)$(PREFIX)/include/star - mkdir -p $(DESTDIR)$(PREFIX)/share/doc/star-mc - cp libsmc.so $(DESTDIR)$(PREFIX)/lib - cp smc.pc $(DESTDIR)$(PREFIX)/lib/pkgconfig - cp src/smc.h $(DESTDIR)$(PREFIX)/include/star - cp COPYING.en COPYING.fr README.md $(DESTDIR)$(PREFIX)/share/doc/star-mc + @$(SHELL) make.sh install "$(DESTDIR)$(PREFIX)/lib" $(LIBNAME) + @$(SHELL) make.sh install "$(DESTDIR)$(PREFIX)/lib/pkgconfig" smc.pc + @$(SHELL) make.sh install "$(DESTDIR)$(PREFIX)/include/star" src/smc.h + @$(SHELL) make.sh install $(DESTDIR)$(PREFIX)/share/doc/star-mc\ + COPYING.en COPYING.fr README.md uninstall: - rm -f $(DESTDIR)$(PREFIX)/lib/libsmc.so - rm -f $(DESTDIR)$(PREFIX)/lib/pkgconfig/smc.pc - rm -f $(DESTDIR)$(PREFIX)/include/star/smc.h - rm -f $(DESTDIR)$(PREFIX)/share/doc/star-mc/COPYING.en - rm -f $(DESTDIR)$(PREFIX)/share/doc/star-mc/COPYING.fr - rm -f $(DESTDIR)$(PREFIX)/share/doc/star-mc/README.md + rm -f "$(DESTDIR)$(PREFIX)/lib/$(LIBNAME)" + rm -f "$(DESTDIR)$(PREFIX)/lib/pkgconfig/smc.pc" + rm -f "$(DESTDIR)$(PREFIX)/include/star/smc.h" + rm -f "$(DESTDIR)$(PREFIX)/share/doc/star-mc/COPYING.en" + rm -f "$(DESTDIR)$(PREFIX)/share/doc/star-mc/COPYING.fr" + rm -f "$(DESTDIR)$(PREFIX)/share/doc/star-mc/README.md" ################################################################################ # Miscellaneous targets @@ -110,10 +122,13 @@ uninstall: all: build_library build_tests clean: clean_test - @rm -f $(OBJ) $(TEST_OBJ) libsmc.so .test smc.pc .config + rm -f $(OBJ) $(TEST_OBJ) $(TEST_OBJ_S3D) $(LIBNAME) image.ppm .test smc.pc .config distclean: clean - @rm -f $(DEP) $(TEST_DEP) + rm -f $(DEP) $(TEST_DEP) $(TEST_DEP_S3D) + +lint: + shellcheck -o all make.sh ################################################################################ # Tests @@ -122,43 +137,53 @@ TEST_SRC =\ src/test_smc_device.c\ src/test_smc_doubleN.c\ src/test_smc_errors.c\ - src/test_smc_light_path.c\ src/test_smc_solve.c - TEST_OBJ = $(TEST_SRC:.c=.o) TEST_DEP = $(TEST_SRC:.c=.d) -test: build_tests - @$(SHELL) make.sh run_test $(TEST_SRC) +# Tests that require Star-3D +TEST_SRC_S3D = src/test_smc_light_path.c +TEST_OBJ_S3D = $(TEST_SRC_S3D:.c=.o) +TEST_DEP_S3D = $(TEST_SRC_S3D:.c=.d) +S3D_FOUND = $(PKG_CONFIG) --atleast-version $(S3D_VERSION) s3d -build_tests: build_library $(TEST_DEP) .test - @$(MAKE) -fMakefile -f.test $$(for i in $(TEST_DEP); do echo -f"$${i}"; done) test_bin +SMC_CFLAGS = $$($(PKG_CONFIG) --with-path=./ $(PCFLAGS) --cflags smc-local.pc) +SMC_LIBS = $$($(PKG_CONFIG) --with-path=./ $(PCFLAGS) --libs smc-local.pc) -.test: Makefile - @echo "Setup tests" - @$(SHELL) make.sh config_test $(PKG_CONFIG) $(TEST_SRC) > .test +build_tests: build_library .test + @$(MAKE) -fMakefile -f.test\ + $$(for i in $(TEST_DEP); do echo -f"$${i}"; done)\ + $$($(S3D_FOUND) && for i in $(TEST_DEP_S3D); do echo -f"$${i}"; done)\ + test_bin -test_run: test_bin +test: build_tests @$(SHELL) make.sh run_test $(TEST_SRC) + @if $(S3D_FOUND); then $(SHELL) make.sh run_test $(TEST_SRC_S3D); fi + +.test: Makefile + @{ $(SHELL) make.sh config_test $(TEST_SRC);\ + if $(S3D_FOUND); then $(SHELL) make.sh config_test $(TEST_SRC_S3D); fi }\ + > $@ clean_test: - @$(SHELL) make.sh clean_test $(TEST_SRC) + @$(SHELL) make.sh clean_test $(TEST_SRC) $(TEST_SRC_S3D) + +$(TEST_OBJ) $(TEST_OBJ_S3D): config.mk smc-local.pc -$(TEST_OBJ): config.mk - @echo "CC $@" - @$(CC) $(CFLAGS) $(INCS) -c $(@:.o=.c) -o $@ +$(TEST_OBJ): + $(CC) $(CFLAGS) $(SMC_CFLAGS) -c $(@:.o=.c) -o $@ -test_smc_device: libsmc.so - @echo "LD $@" - @$(CC) $(CFLAGS) -fopenmp -o $@ src/$@.o -L$$(pwd) -lsmc $(LIBS) +test_smc_device: + $(CC) -o $@ src/$@.o $(LDFLAGS) $(SMC_LIBS) -fopenmp -test_smc_doubleN\ +test_smc_doubleN \ test_smc_errors \ test_smc_solve \ -: libsmc.so - @echo "LD $@" - @$(CC) $(CFLAGS) -o $@ src/$@.o -L$$(pwd) -lsmc $(LIBS) +: + $(CC) -o $@ src/$@.o $(LDFLAGS) $(SMC_LIBS) -lm + +$(TEST_OBJ_S3D): + $(CC) $(CFLAGS) $(SMC_CFLAGS) $(S3D_CFLAGS) -c $(@:.o=.c) -o $@ -test_smc_light_path: libsmc.so - @echo "LD $@" - @$(CC) $(CFLAGS) -o $@ src/$@.o -L$$(pwd) -lsmc $(LIBS) $(STAR-3D_LIB) +test_smc_light_path: + $(CC) $(CFLAGS) $(SMC_CFLAGS) $(S3D_CFLAGS) -o $@ src/$@.o $(LDFLAGS) $(SMC_LIBS) $(S3D_LIBS) -lm diff --git a/config.mk b/config.mk @@ -1,41 +1,71 @@ VERSION = 0.5.0 - PREFIX = /usr/local + +LIB_TYPE = SHARED +#LIB_TYPE = STATIC + +BUILD_TYPE = RELEASE +#BUILD_TYPE = DEBUG + +################################################################################ +# Tools +################################################################################ +AR = ar +CC = cc PKG_CONFIG = pkg-config +RANLIB = ranlib ################################################################################ # Dependencies ################################################################################ +PCFLAGS_SHARED = --shared +PCFLAGS_STATIC = --static +PCFLAGS = $(PCFLAGS_$(LIB_TYPE)) + RSYS_VERSION = 0.6 -RSYS_INC = $$($(PKG_CONFIG) --cflags rsys) -RSYS_LIB = $$($(PKG_CONFIG) --libs rsys) +RSYS_CFLAGS = $$($(PKG_CONFIG) $(PCFLAGS) --cflags rsys) +RSYS_LIBS = $$($(PKG_CONFIG) $(PCFLAGS) --libs rsys) STAR-SP_VERSION = 0.12.1 -STAR-SP_INC = $$($(PKG_CONFIG) --cflags star-sp) -STAR-SP_LIB = $$($(PKG_CONFIG) --libs star-sp) +STAR-SP_CFLAGS = $$($(PKG_CONFIG) $(PCFLAGS) --cflags star-sp) +STAR-SP_LIBS = $$($(PKG_CONFIG) $(PCFLAGS) --libs star-sp) -# Optional -STAR-3D_VERSION = 0.4 -STAR-3D_INC = $$($(PKG_CONFIG) --cflags s3d) -STAR-3D_LIB = $$($(PKG_CONFIG) --libs s3d) +# Optional (for test only) +S3D_VERSION = 0.4 +S3D_CFLAGS = $$($(PKG_CONFIG) $(PCFLAGS) --cflags s3d) +S3D_LIBS = $$($(PKG_CONFIG) $(PCFLAGS) --libs s3d) -INCS=$(RSYS_INC) $(STAR-SP_INC) -LIBS=$(RSYS_LIB) $(STAR-SP_LIB) +DPDC_CFLAGS = $(RSYS_CFLAGS) $(STAR-SP_CFLAGS) +DPDC_LIBS = $(RSYS_LIBS) $(STAR-SP_LIBS) -lm ################################################################################ # Compilation options ################################################################################ -CC = cc - -CPPFLAGS = -DNDEBUG WFLAGS =\ -Wall\ + -Wcast-align\ -Wconversion\ -Wextra\ -Wmissing-declarations\ -Wmissing-prototypes\ -Wshadow -CFLAGS = -O3 -std=c89 -pedantic -fPIC -fvisibility=hidden -fstrict-aliasing\ - -Wl,--no-undefined $(WFLAGS) $(CPPFLAGS) # Compiler options -LDFLAGS = -shared # Linker options +CFLAGS_COMMON =\ + -pedantic\ + -fPIC\ + -fvisibility=hidden\ + -fstrict-aliasing\ + $(WFLAGS) + +CFLAGS_RELEASE = -O2 -DNDEBUG $(CFLAGS_COMMON) +CFLAGS_DEBUG = -g $(CFLAGS_COMMON) +CFLAGS = $(CFLAGS_$(BUILD_TYPE)) + +################################################################################ +# Linker options +################################################################################ +SOFLAGS = -shared -Wl,--no-undefined + +LDFLAGS_DEBUG = +LDFLAGS_RELEASE = -s +LDFLAGS = $(LDFLAGS_$(BUILD_TYPE)) diff --git a/make.sh b/make.sh @@ -33,59 +33,51 @@ config_test() { - if [ $# -lt 2 ]; then - echo "usage: config_test pkg-config [src ...]" >&2 - exit 1 - fi - - PKG_CONFIG="$1" - shift 1 - for i in "$@"; do - test=$(echo "${i}" | sed 's/src\/\(.\{1,\}\).c$/\1/') - - if ! [ ${test} == "test_smc_light_path" ] \ - || "${PKG_CONFIG}" --exists s3d; then - test_list="${test_list} ${test}" - printf "%s: %s\n" "${test}" "src/${test}.o" - fi + test=$(basename "${i}" ".c") + test_list="${test_list} ${test}" + printf "%s: src/%s.o\n" "${test}" "${test}" done printf "test_bin: %s\n" "${test_list}" } run_test() { - n=0 - for i in "$@"; do - test=$(echo "${i}" | sed 's/src\/\(.\{1,\}\).c$/\1/') - - if [ ! -f "${test}" ]; then - continue; - fi + test=$(basename "${i}" ".c") printf "%s " "${test}" - - # Using sh -c to handle segfault messages - if sh -c "./\"${test}\" &> /dev/null 2>&1" 2> /dev/null; then + if "./${test}" > /dev/null 2>&1; then printf "\e[1;32mOK\e[m\n" else printf "\e[1;31mErreur\e[m\n" - n=$((n+1)) fi - done - - if [ "${n}" -ne 0 ]; then - printf "%d errors\n" "${n}" - exit 1 - fi + done 2> /dev/null } clean_test() { for i in "$@"; do - test=$(echo "${i}" | sed 's/src\/\(.\{1,\}\).c$/\1/') - rm -f "${test}" + rm -f "$(basename "${i}" ".c")" + done +} + +install() +{ + prefix=$1 + shift 1 + + mkdir -p "${prefix}" + + for i in "$@"; do + dst="${prefix}/${i##*/}" + + if cmp -s "${i}" "${dst}"; then + printf "Up to date %s\n" "${dst}" + else + printf "Installing %s\n" "${dst}" + cp "${i}" "${prefix}" + fi done }