Old .Po file references old directory, how to start fresh? - makefile

Introduction
I just deleted the directory nested and removed the reference to it in my Makefile.am
I'm running ./configure && make and I get the following:
*** No rule to make target 'nested/main.c', needed by 'main.o'. Stop.
How can I run make so that it doesn't reference old directories?
Supplemental Info
I was curious if I could find where this reference is, so I did a grep -r nested . I think the only relevant hit is:
./src/.deps/main.Po:main.o nested/main.c /usr/include/stdc-predef.h /usr/include/stdio.h \

Answering this question from OP's comment:
Run
make distclean

Related

Can define a rule in GNU Make to unconditionally create a symlink at the start of every make?

I need to create a symlink to some of the code that make should compile. Can I get GNU Make to create the symlink unconditionally at the start of every make?
Background: I am running make in a test directory; the source to be tested is in a directory ../application/src relative to where I run make. Make and GCC are fine with the source being outside the work directory, but one of the tools for reporting my coverage can't handle it. Hence the symlink, so everything is under the work directory.
What I have tried is to create a rule to make the link
appsrc:
ln -s ../application/src/ appsrc
And I made this a prerequisite of the rule to make .o files from the ../application/src files:
obj/%.o : appsrc/%.cpp appsrc
$(CC) $(CFLAGS) -o ./obj/$(#F) -c $<
but it did not work. Not 100% sure why, I tried to understand the output of make -d but it's difficult -- I think it fails to find the appsrc/%.cpp file so does not get as far as running the appsrc rule.
So I added this rule:
appsrc/%: ../application/src/% appsrc
Now when make fails to find an application source file, say appsrc/foo.cpp, but can see ../application/src/foo.cpp, it knows to run the appsrc rule.
And that worked -- once. But after that, it stopped working. Why? because now appsrc/foo.cpp is an "intermediate file", and there's no explicit rule to make it, so make went and deleted any such files! So now some of my source files are gone! Thank goodness for version control...
To prevent this I think I need to get rid of the appsrc/% rule. So can I replace it with something that will get run unconditionally? What would the syntax for that be in GNU Make?
Why not just do it in a $(shell ...) function?
_dummy := $(shell ln -f -s ../application/src/ appsrc)
will run when the makefile is parsed.

make dependency on all files in a subdirectory (git submodule)

I want to write a (GNU) make rule that depends on the existence of some file (any arbitrary file) in a subdirectory. In my specific case, that subdirectory is a git submodule.
This is what I have:
DEP = submod/.git
$(DEP):
git submodule update --init $(#D)
submod/%: | $(DEP)
# # why do I need this?
install: submod/junk.c
echo installing
If I then type make install, the git command is run (change it to mkdir -p $(#D); touch $# for a non-git-specific test), and make doesn't complain.
I have two questions. Primarily, are there any side effects to the dummy recipe for submod/% I should be concerned about? Secondly, and more interestingly, why do I need that recipe at all? If I remove it, make errors out:
make: *** No rule to make target 'submod/junk.c', needed by 'install'. Stop.
My only hypothesis is that make is doing some optimization based on the files that exist at startup, and with the no-recipe version, it thinks that it can just expect the file to exist when it's needed, but with any recipe there, it can't do that optimization, and it reevaluates when it's needed. If that's true, is it a bug, or something that should be changed?

Makefile pattern rules not working

I am learning makefiles, and can't just wrap my head around this problem i am having, and would like to understand how/why this fail.
I have half a dozen erlang files in a src directory. I want to compile these into a ebin directory, without having to define a rule for each and every one of them. According to the Gnu make documentation, pattern rules should be right up my alley.
However, with the following makefile, all I get from make is make: *** No targets. Stop. Why is that?
ebin/%.beam: src/%.erl
mkdir -p ebin
erlc -o ebin $<
Edit: Based on this answer, I now understand that i would have to explicitly declare the targets, for instance by using make ebin/cmplx.beam. However, i still do not understand how i should write my makefile to get my desired behaviour - since I have half a dozen targets (and in other projects even more), this seems like an unnecessary hassle. Is there not a way to define targets based on the source file names?
The target rule tells make that whenever it needs to produce a beam file in the ebin directory, and there exists a corresponding erl file in the src directory, it can use erlc.
However, this doesn't tell make that this is what it needs to do. You could explicitly tell make what it needs to do by giving it a target on the command line:
make ebin/foo.beam
If you don't give a target on the command line, make will pick the first non-pattern rule in the makefile as its target. However, your makefile doesn't have any non-pattern rules, so there is no target.
What you probably want is that for each existing erl file in src, make should consider the corresponding beam file in ebin to be a target. You can achieve that by calling wildcard and patsubst:
erl_files=$(wildcard src/*.erl)
beam_files=$(patsubst src/%.erl,ebin/%.beam,$(erl_files))
ebin/%.beam: src/%.erl
mkdir -p ebin
erlc -o ebin $<
all: $(beam_files)
(The indented lines need to be actual physical tabs, not spaces.)
That way, running make will rebuild all beam files that are out of date. all gets chosen as the default target, and it in turn depends on all beam existing or potential, each of which in turn depends on the corresponding erl file.
This trick is described in the GNU make manual.

Difficulties with a Makefile

So I'm trying to install the Homotopy Type Theory library for Coq from github following these instructions. Running the command etc/install_coq.sh sets it off messing with a bunch of files before it hits an error as so:
$ make clean
make: *** No rule to make target `clean'. Stop.
Apparently there's one or more bugs present within Makefile.am, and according to what I've read while googling the issue it's likely related to improper whitespace. Running make clean myself yields the same thing:
make: *** No rule to make target `clean'. Stop.
Meanwhile running make -f Makefile.am clean yields:
Makefile.am:4: *** missing separator. Stop.
Lines 4-6 in the file are simply:
if make_hoqide
bin_SCRIPTS += hoqide
endif
What's wrong with that that's causing the problem?
Makefile.am is generally paired with Makefile.in; these need to be processed with automake or configure before you get a usable real Makefile.
If you've got a script "autogen.sh" in your top-level source directory, run that
first, then configure:
$ ./autogen.sh
$ ./configure
$ make
This is, in fact, step 3 of the instructions that you linked to. Perhaps the install_coq.sh script isn't finding all of the dependencies that you need?

make: Nothing to be done for `all'. on Target That Just Calls Another Makefile

Say I have the following gnu makefile.
TOP := $(dir $(lastword $(MAKEFILE_LIST)))
all : graphics
graphics :
pushd $(TOP)../graphics; \
$(TOP)../tools/autotools_gen.sh; \
./configure; \
$(MAKE) clean all; \
$(TOP)../tools/autotools_clr.sh; \
popd;
inside a folder called build and I call it from one directory up, in the following manner:
make --file ./build/Makefile all
and I get the following message from make:
make: Nothing to be done for `all'.
Why is it complaining that there is nothing to be done for all?
The problem you run into is that because you have a directory graphics (I took this from the question comments) in the working directory, when make encounters the target
graphics :
as a prerequisite for all, it sees that graphics already exists, that none of its prerequisites are newer than it (because it doesn't have any), and so considers it up to date and does nothing to build it. Since all doesn't have a recipe of its own, make then doesn't find anything to do for it either and just tells you that there's nothing to do.
The solution is to declare graphics and all as phony targets:
.PHONY: all graphics
Then they will be run even if files or directories called all or graphics exist/are newer than their dependencies.
The intent of phony targets is to make rules that don't produce a file work properly even if such a file accidentally appears in the directory of the Makefile, so it is commonly used for targets all, clean, install and suchlike. Your graphics target doesn't produce a file graphics, so it falls into this category.
See also this section in the GNU make manual (which also applies to other makes).

Resources