On Fri, 2009-06-05 at 00:46 -0400, Paul Smith wrote: > > //%: //% > > @echo oops! > > When I run this with GNU make 3.80, I get this error: > > make: Circular /tmp/x1.mk <- /tmp/x1.mk dependency dropped. > > Is that what you mean by "normal"? > > I do agree that something is broken in the circular prerequisite > detection in 3.81 (and even in current CVS) because these versions of > make don't notice the circularity and tries to continuously to create > a new dependency until it goes over some limit
OK, I've investigated this. It's a bizarre confluence of different events. First up, there's apparently a bug in the current glibc implementation of glob(3) on my system. When I run glob() and pass it the pattern "//%" and the GLOB_NOCHECK option, which is how GNU make invokes it in this situation, it should (according to the POSIX standard) return the input pattern unmodified (since the glob pattern doesn't match anything--I'm assuming that you, like me, do not have a file "/%" on your system). However, what it ACTUALLY does is return "/%", stripping off the initial "/". So, when make internalizes this pattern instead of storing the string "//%" as the pattern, it's storing "/%" and that's why /tmp/x1.mk is matching. It's even weirder because if you use something like "///%" then you get back the right thing ("///%"). If you use "//%/" you get back the right thing. It's only two slashes followed by a word (no more slashes) that you get this bug. If you have an implementation of glob() that more carefully follows the POSIX standard then you'll get "//%" and your version of make could behave differently, and you won't get the circular dependency dropped error like I did. So, that's the first thing. The second thing is why you get the circular dep error in 3.80 and basically an infinite loop in 3.81. In 3.80, GNU make also ran the glob() function over the prerequisites, which also stripped off the leading "/", so REALLY what I get with that release is: /% : /% and it's obvious why there's a circular dep error. However, as part of the second expansion code, BorisK deferred the glob() call on the prerequisites list until later. Then apparently (I didn't track this in detail) for pattern rules the glob() is never actually run. In a way this makes sense since globbing a pattern is not what you want. But because of this, the prerequisite path is never "sanitized" to remove the leading duplicate "/", and so in 3.81 and above this rule reduces to: /% : //% Well, now you can clearly see why we are getting infinite recursion here. Less obvious is which of the various ways it could be fixed is the right way. Should we stop "cleaning" these paths altogether, to work around the bug in glibc glob()? I think if we removed the GLOB_NOCHECK flag from glob() then handled the GLOB_NOMATCH error correctly we could avoid that problem. Should we go back to globbing the patterns? Seems like overkill to me, and potentially wrong. -- ------------------------------------------------------------------------------- Paul D. Smith <psm...@gnu.org> Find some GNU make tips at: http://www.gnu.org http://make.mad-scientist.us "Please remain calm...I may be mad, but I am a professional." --Mad Scientist _______________________________________________ Bug-make mailing list Bug-make@gnu.org http://lists.gnu.org/mailman/listinfo/bug-make