[gnu.utils.bug] make 3.55 infinite loop

grady@fxgrp.fx.com (Steven Grady) (08/31/89)

It seems like the new feature that a production that has commands
but no dependencies should always be executed is a mistake.  I believe
this should only be the case if it is a phony target.  If it's a real
file, then a valid interpretation of having no dependencies is that
this is the set of commands to do to _create_ the file.  If the file
exists, no commands need to run.

I'm not sure I am right about this, however.  If you are still interested,
keep reading -- I'll describe the problem I'm having in detail.

I have a makefile system that is kind of complicated.  I include
a file called $(DEPENDENCIES), which is in an architecture-dependent
subdirectory.  In this case, I'm running the program on a sun3.
$(DEPENDENCIES) (in this case, "sun3/Dependencies") has a production
to create it from the "Dependencies" file in the current directory.
This "Dependencies" file is modified by mkmf.  Furthermore, if
the "Dependencies" file doesn't exist (ie the first time you run
the make), it will be copied from a template file (in my case,
a file called "/usr/aws/etc/GnuMake/DependTmpl").

The idea is that if you do a "gnumake depend", the "Dependencies" file 
gets created, then updated.  If you then do a "gnumake" (on a sun3),
the "sun3/Dependencies" file depends on "Dependencies", so it gets
updated.  This new "sun3/Dependencies" file is then included.

This all worked fine until 3.55.  Under 3.55, if I say "gnumake",
it starts going into an infinite loop, saying the following:
  cp /usr/aws/etc/GnuMake/DependTmpl Dependencies
  chmod ug+w Dependencies
  gnumake depend
  cp /usr/aws/etc/GnuMake/DependTmpl Dependencies
  chmod ug+w Dependencies
  gnumake depend
  ...

When I run it with "-d", here is the beginning of the output:
  Reading makefiles...
  Updating makefiles....
    Considering target file `sun3/Dependencies'.
     Considering target file `Dependencies'.
      Finished dependencies of target file `Dependencies'.
     Target `Dependencies' has commands but no dependencies.
     Must remake target `Dependencies'.

Here is the relevant rule:
$(DEPENDFILE):
        cp $(MAKEDIR)/DependTmpl $(DEPENDFILE)
        chmod ug+w $(DEPENDFILE)
        $(MAKE) depend

What's happening is that the file gets copied (since it has commands
but no dependencies), then gnumake gets re-invoked.  It then runs the
same rules, causing gnumake to be re-invoked, etc.

	Steven
	...!ucbvax!grady
	grady@postgres.berkeley.edu

"Guards, beat this man brutally for daring to try to confuse me!"

grady@fxgrp.fx.com (Steven Grady) (08/31/89)

[Sorry these are so long.]
Hmm.  On looking at this further, I see a more insidious problem.
Consider the siuation where you want to include one makefile
in another, but you want to provide the opportunity for
overriding productions (which is what I want to do).  This
requires using a ".DEFAULT" rule (as recommended in the "Overriding
Makefiles" section of the texinfo document).  But consider the
following makefile:
	a: b
		@echo making a
	
	.DEFAULT:
		$(MAKE) -f OtherMakefile $@

The default production, a, depends on b.  Assume b exists.  Well,
since there is a default production, b has commands associated with it 
(namely, the commands in the default production which are used whenever
no other productions can be found).  Since b has commands but no dependencies,
the default rule will be executed.  So it's going to invoke another
make just because it can't find any production on what to do for a file
that already exists.

If there were an additional line up there: "include a", then even if
some other production were invoked, it would still check if "a" was
up-to-date (since all include files are checked), and therefore the
default rule would fire to try to update "b".

It also seems to be the case that gnumake always checks to see if
the makefile being used is up-to-date.  Again, if there's a default 
production, gnumake will try to use it to update the makefile itself,
meaning that gnumake will _always_ be invoked at least twice if there's
a DEFAULT production.

I think I've made my point that firing off commands if there are no 
dependencies, combined with DEFAULT productions, is a bad thing.  I'm 
not sure what the right fix would be, but it seems that if there are 
no dependencies, commands should only be executed if the target is PHONY.

	Steven
	...!ucbvax!grady
	grady@postgres.berkeley.edu

"But Calvin is no kind and loving god!  He's one of
the _old_ gods!  He demands sacrifice!"

fkittred@bbn.com (Fletcher Kittredge) (08/31/89)

In article <1989Aug31.014333.18904@fxgrp.fx.com> grady@fxgrp.fx.com (Steven Grady) writes:
>It seems like the new feature that a production that has commands
>but no dependencies should always be executed is a mistake.

If you are talking about the feature that if I have the two line makefile

foo:
	@echo hello

that hello is echoed, then you are wrong that this is a new feature.  This
has been in every version of make I run across (many versions!). In addition,
it is documented in Feldman's orignal 1978 article describing make, "Make -
A Program for Maintaining Computer Programs".  For gmake not to include
this feature would break many makefiles and backwards compatability.

regards,
fletcher
Fletcher E. Kittredge  fkittred@bbn.com

grady@fxgrp.fx.com (Steven Grady) (09/01/89)

In article <45050@bbn.COM> fkittred@BBN.COM (Fletcher Kittredge) writes:
>In article <1989Aug31.014333.18904@fxgrp.fx.com> grady@fxgrp.fx.com (Steven Grady) writes:
>>It seems like the new feature that a production that has commands
>>but no dependencies should always be executed is a mistake.
>
>If you are talking about the feature that if I have the two line makefile
>
>foo:
>	@echo hello
>
>that hello is echoed, then you are wrong that this is a new feature.

No, I'm describing something else.  If I have the following makefile:

    bar: foo
	    @echo bar
    foo:
	    @echo foo

Also, assume "foo" already exists.

Sun's make and gnumake 3.54 do the same thing:
	% make
	bar

Gnumake 3.55 does this:
	% make
	foo
	bar

The important point is that before, a file without dependencies was 
considered up-to-date if it existed.  Now, it's never considered up-to-date
if there are any commands associated with the production.  The current
form is inconsistent with other versions of make.

	Steven
	...!ucbvax!grady
	grady@postgres.berkeley.edu

If God had wanted us to be concerned for the plight of the toads, he would
have made them cute and furry. 

mcgrath%saffron.Berkeley.EDU@GINGER.BERKELEY.EDU (Roland McGrath) (09/01/89)

Yes, this was a bug.  I've fixed it.