I don't know how to make a dependence rule within * inside
as: folder1/folder2/*/sch.oa
to the target:
folder3/*.scs
Thanks in advance for your help
Just write a pattern rule:
folder3/%.scs: folder1/folder2/%/sch.oa
#echo building $# from $<
EDIT: to build all such files, first find all such sch.oa files:
SOURCES := $(wildcard folder1/folder2/*/sch.oa)
then calculate the corresponding targets:
TARGETS := $(patsubst folder1/folder2/%/sch.oa,folder3/%.scs, $(SOURCES))
Then you can write a simple rule that has them as its prerequisites.
Related
I've been looking through makefile syntax manuals and haven't found anything that really helps the usage case I'm trying to enact here.
What I have is a list of source files with varying directories under a common directory, like so:
src/a.h
src/b.h
src/dir/c.h
src/dir/dir/d.h
and would like make to use these individually as a dependency for a rule that ultimately creates:
build/a.h
build/b.h
build/c.h
build/d.h
which then are used as dependencies individually for more rules.
What I have so far:
LIST := src/a.h src/b.h src/dir/c.h src/dir/d.h
all : $(addprefix build/,$(notdir ${LIST}))
#echo 'All rule invoked'
What doesn't work:
$(LIST) : build/$(notdir %).h : %.h
#echo 'dst $* dat $# din $<'
target 'item' doesn't match the target pattern
build/%.h: %.h
no rule to make target 'build/a.h' needed by 'all'.
I'm guessing make got mad at me at this point, as the errors started telling me to stop.
Basically, I am reading in a list of files with a path prefix that is relevant for the search path and dependency, and want to dump each individual one only when the source file is updated. After this, these files in that single directory are used as dependencies for another batch of rules. How can I accomplish this?
Note: I've gotten it done by ignoring the dependency chain, but that's not going to work. I can also use make to run scripts that generate an explicit makefile that can do it properly, but that feels like overkill and a waste of resources, and make ought to be able to create a rule that does that by itself, as powerful as it is. I just don't know how to create generic rules that focus on the dependency variable for its text matching, rather than the target.
There's no good way of using a pattern rule here, as all the headers are (potentially) in different directories and you want to move them out to a common directory. If you're using GNU make, you can write a macro rule that expands to all the rules you need:
define copy_header_rule
build/$(notdir $(1)): $(1)
cp $$< $$#
endef
$(foreach hdr,$(LIST),$(eval $(call copy_header_rule,$(hdr))))
This goes through each of the headers in your $(LIST) a creates a rule to copy it to the build directory
You can make things pretty simple with vpath:
TARGS:= $(addprefix build/, $(notdir $(LIST)))
vpath %.h $(dir $(LIST))
all: $(TARGS)
build/%.h: %.h
#echo building $# from $<
...
To build multiple executables from the same source, I have to translate every source file with different Compiler Switches. For every variant, I have a set of defines to be set. I want to store the resulting object files into different subfolders. I have a variable, keeping all object file from all variants. Now I have problems to define a proper static rule to build the object files from the sources:
SOURCEEXT=.c
ALL_OBJECT_FILES := abcdefg/cctalkio.o tollcoll/cctalkio.o
source-from-object = $(addsuffix $(SOURCEEXT),$(basename $(notdir $(1))))
$(ALL_OBJECT_FILES): %.o: $(call source-from-object,%.o)
#echo $*.o
when I run make abcdefg/cctalkio.o, I get:
make: *** No rule to make target 'abcdefg/cctalkio.c', needed by 'abcdefg/cctalkio.o'. Schluss.
The same, when I simpify the rule to:
abcdefg/cctalkio.o: %.o: $(call source-from-object,%.o)
#echo $*.o
But when I change the rule to:
abcdefg/cctalkio.o: %.o: $(call source-from-object,abcdefg/cctalkio.o)
#echo $*.o
I get abcdefg/cctalkio.o as Output. So the stem seems to be abcdefg/cctalkio, thus %.o should be the same as abcdefg/cctalkio.o. But why is make behaving different in both cases?
When I "debug" the source-from-object function:
debug:
#echo $(call source-from-object,/abcdefg/cctalkio.o)
I get the expected result cctalkio.c, so it seem like the function is working.
Your $(call) in the prereq is happening immediately and so your function is actually being passed %.o (not the matched result as you expected).
You would have to use something like:
.SECONDEXPANSION:
abcdefg/cctalkio.o: %.o: $$(call source-from-object,%.o)
...
to get what you want I believe.
Alternatively you could probably loop over your object files and statically give them the correct prerequisites and just let the static pattern rule supply the body.
I want to compile some C++ files and I absolutely have to put all object files in a separate build directory, but stored completely flat, i.e., without any further subdirectories. I know the common solution using VPATH, which goes something like this:
SOURCES = foo/one.cpp \
foo/bar/two.cpp \
foo/bar/sub/three.cpp
OBJDIR = obj
VPATH=$(dir $(SOURCES))
OBJECTS = $(addprefix $(OBJDIR)/, $(notdir $(SOURCES:%.cpp=%.o)))
$(OBJDIR)/%.o : %.cpp
#echo Should compile: $(filter %/$*.cpp, $(SOURCES))
#echo Compiling $<
all: $(OBJECTS)
This example pretty much works: I get three object files one.o, two.o, three.o in the 'obj' subdirectory (you can assume it just exists).
Now here's the catch when using VPATH: If there happens to be a file 'foo/three.cpp', then this will be compiled instead of the 'foo/bar/sub/three.cpp' which is named in the SOURCES variable. And no, I cannot rename either file; this name clash simply exists and I cannot do anything about that.
So my question is: How can I tell Make to only use '.cpp' files which appear in the SOURCES variable? I think the best solution would be to use that 'filter' statement in the target's prerequisite. I think this should be possible using secondary expansion, but I don't know what to do with the '%'. For example, I tried
.SECONDEXPANSION:
$(OBJDIR)/%.o : $$(filter %/$$*.cpp, $(SOURCES))
but that doesn't work.
UPDATE: With the help of tripleee, I managed to get this working using the following:
define make-deps
$(OBJDIR)/$(notdir $(1:%.cpp=%.o)): $1
endef
$(foreach d, $(SOURCES), $(eval $(call make-deps,$d)))
%.o :
#echo Should compile $^ into $#
#echo Compiling $^
I suspect the easiest solution to your problem would be to get rid of VPATH and document each dependency explicitly. This can easily be obtained from your SOURCES definition; perhaps you want to define a function, but it really boils down to this:
obj/one.o: foo/one.cpp
obj/two.o: foo/bar/two.cpp
obj/three.o: foo/bar/sub/three.cpp
The actual rule can remain, only it should no longer contain the dependencies in-line, and you can skip the obj/ subdirectory, because it's declared explicitly in each dependency:
%.o : # Dependencies declared above
#echo Should compile $^ into $#
#echo Compiling $^
I changed the rule to use $^ instead of $< in case you ever have more than a single dependency. This may be right or wrong for your circumstances; revert the change if it's not what you need.
In order to not need to maintain the dependencies by hand, you might want to generate %.d for each %.cpp file. See the GNU Make manual. (I tried to do this by using a define, but it seems you cannot declare dependencies with a foreach loop.)
In response to the question in the comment, this should not affect parallel builds in any way; it merely disambiguates the dependencies where your original Makefile was ambiguous when there were multiple biuld candidates with the same name in the VPATH. There are no new dependencies and no new rules.
I am trying to do this:
From a directory, pick all the C (.c) files, generate .o and add it to
my final target executable. The C files can be added or removed at anytime, so when I
run make for my target, the available C files from the directory has to be picked
to compile and link with my target.
So far, I have the following:
define test_tgt =
DIR = full/path/to/dir
FILES = $(wildcard $(DIR)/*.c)
OBJS = <rule-to-convert-C-to-O>
endef
get_new_files:
$(eval $(test_tgt))
final-target: get_new_files
$(CC) <other-objs> $(OBJS)
Somehow this doesn't seem to work. I see a lot of similar examples, but not sure what
is wrong here. If this approach is not correct, can anyone suggest a better way to
accomplish this.
TIA.
You are trying to program a check that make does by itself.
Just list $(OBJS) as dependencies of final-target.
Something like this should work under GNU make:
DIR = full/path/to/dir
FILES = $(wildcard $(DIR)/*.c)
OBJS = $(subst .c,.o,$(FILES))
final-target: $(OBJS)
$(LD) -o $# $+ # or similar
Full documentation is here: https://www.gnu.org/software/make/manual/html_node/Text-Functions.html
A common type of makefile has a line like this:
OBJS=something.o other.o third.o progname.o
progname: $(OBJS)
Then you would run make progname. But GNU Make can also generate the list of o-files itself from all the c-files it sees in the current directory. How is this done?
Basically, I want to be able to add C files to the directory without having to change the makefile.
(Is it for instance through some shell-magic, or is there is a built-in function for this?)
It can also be done like this:
SRCS = $(wildcard *.c)
OBJS = $(SRCS:.c=.o)
progname: $(OBJS)
Which works just fine if the object file with main() in it is "progname.o".
To view all the defined rules (include the implicit ones), issue make -p.
However the fact that make knows how to generate object files from source files, does not mean that it should do this. Make will try to do the bare minimum in order to satisfy the target you ask it to build.
If you want make to compile all the sources into object in the current directory you will need a rule that will depend on all the objects, e.g.:
all: $(patsubst %.c,%.o,$(wildcard *.c))
You can expand a shell command to give you a list of files. You can also use implicit rules.
It can be done like this:
$(ODIR)/%.o: %.cpp
$(CC) -c $(CFLAGS) -o $# $<
make generates .o file names from .cpp file names it found in the current directory.