Originally I wanted to automatically include helpers to unit-test static functions by using --include gcc keyword like described in the link below:
The idea is to automatically include a foo.cu ( c/c++ for unit ) making calls to static functions defined in foo.cc
I read several answers like
How to conditional set up a Makefile variable by testing if a file exists
Define make variable at rule execution time
How do I check if file exists in Makefile so I can delete it?
but syntax like the one below was not successful (even with characters alignment to the target...)
#did not work
ifneq ($(wildcard $(UT_FILE_LOC)),)
$(eval LOC_CPPFLAGS := $(CPPFLAGS) --include $(UT_FILE_LOC))
else
$(eval LOC_CPPFLAGS := $(CPPFLAGS) )
endif
and I ended-up with syntax
$(eval LOC_CPPFLAGS := $(shell [[ -e $(UT_FILE_LOC) ]] && echo $(CPPFLAGS) --include $(UT_FILE_LOC) || echo $(CPPFLAGS) ))
Question: Is this a correct way to modify/orientate the value of a makefile variable ?
=========================================================
MCVE for the makefile itself
SRCDIR = src
SRCFILES = $(wildcard src/*.cc)
OBJDIR = obj
DEPDIR = dep
OBJFILES = $(patsubst %.cc,$(OBJDIR)/%.o, $(SRCFILES))
DEPFILES = $(patsubst %.cc,$(DEPDIR)/%.d, $(SRCFILES))
#just some flags for this MCVE
CPPFLAGS = -std=c++11 -Wall -Weffc++
main: $(OBJFILES)
g++ -o $@ $^
# Include dependencies ( change in foo.cu are seen )
-include $(DEPFILES)
$(OBJDIR)/%.o: %.cc
@echo '> Compiling source file: $<'
@install -d $(OBJDIR)/$(dir $<)
@install -d $(DEPDIR)/$(dir $<)
$(eval UT_FILE_LOC := $(patsubst %.cc,%.cu,$<))
$(eval LOC_CPPFLAGS := $(shell [[ -e $(UT_FILE_LOC) ]] && echo $(CPPFLAGS) --include $(UT_FILE_LOC) || echo $(CPPFLAGS) ))
g++ -c $(LOC_CPPFLAGS) -MMD -MP -MF"$(DEPDIR)/$*.d" -o $@ $<
clean:
$(RM) -r $(OBJDIR)/*
$(RM) -r $(DEPDIR)/*
and with basic C++ files (foo.cc, foo.cu and main)
#include <iostream>
static void foo() {
std::cout << "foo" << "\n" << std::flush;
}
void bar() { foo(); } //avoid unused foo() warning for this MCVE
static void foo();
void ut_foo() {
return foo();
}
void ut_foo();
int main(int argc, char* argv[]) {
ut_foo();
return 0;
}
--include src/foo.cu is visible for foo.cc compilation and not for the other files (well, here just the main...).
> Compiling source file: src/foo.cc
g++ -c -std=c++11 -Wall -Weffc++ --include src/foo.cu -MMD -MP -MF"dep/src/foo.d" -o obj/src/foo.o src/foo.cc
> Compiling source file: src/main_unit.cc
g++ -c -std=c++11 -Wall -Weffc++ -MMD -MP -MF"dep/src/main_unit.d" -o obj/src/main_unit.o src/main_unit.cc
g++ -o main obj/src/foo.o obj/src/main_unit.o
./main
foo
Interestingly foo.cu appears in foo.o dependency and a change to foo.cu restart the compilation of foo.c (so no extra work to be done for this point)
obj/src/foo.o: src/foo.cc src/foo.cu
src/foo.cu:
=========================================================