On 1/6/13 Jan 6 -2:44 PM, Faré wrote:
On Sun, Jan 6, 2013 at 3:26 PM, Robert Goldman rpgoldman@sift.info wrote:
This one I think is relevant to the proposed reorganization of ASDF to have changes in upstream systems trigger recompilation in systems that depend on them.
I have made a crude component which is a MADE-FILE. The made-file is built by invoking make to produce some output file.
[...snip...]
OK, so since it's already working, I assume it's respecting the constraints of ASDF, which is that planning happens before any Lisp computation.
I see two cases: 1- The computation that creates your MADE-FILE doesn't depend on any Lisp computation. Then you could either 1a- systematically perform this Make computation BEFORE the Lisp build, and have OPERATION-DONE-P return T, or 1b- (that's ugly) have this computation does during OPERATION-DONE-P itself, and return T or NIL depending on whether things have changed. Actually, I don't recommend that at all: since OPERATION-DONE-P is called *after* OUTPUT-FILES timestamps have been checked, this would be bad. But maybe that's a bug in ASDF, and we should run OPERATION-DONE-P first (unless we are JUST-DONE). 2- The computation that creates your MADE-FILE *does* depend on some previous Lisp computation. Then the only solution is to have this computation be a deterministic product of files that you can all declare as COMPONENTs of your system as STATIC-FILEs if need be, and/or have its INPUT-FILES return (a superset of) the set files from which it will be computed. Then OPERATION-DONE-P can just return T.
I'm not entirely sure I understand your point 2. If the makefile is correct, it will have all of the dependencies, and these can be computed by examining the file system.
Assuming that we keep the current technique of always running make and allowing IT to determine whether the made-file needs rebuilding, the only thing we need to do is to ensure that make is not run too early. That is, we must ensure that all the necessary lisp outputs are written into the filesystem before "make" is invoked.
Hm. I suppose that does rule out your 1a as a technique, assuming we'd like to develop a MADE-FILE class that can be used correctly whether or not it depends on lisp computations.
WRT your 1b, why would it be bad to do this because it's called after OUTPUT-FILES timestamps have been checked? Since we don't have the INPUT-FILES for the MADE-FILE, we can't use the INPUT-FILES/OUTPUT-FILES relationship to determine whether or not the operation needs doing, right?
I was thinking that your 1b could be implemented as
(defmethod operation-done-p ((op compile-op) (c made-file)) (assert (= 1 (length (output-files op c)))) (let* ((output-file (first (output-files c))) (old-write-date (file-write-date output-file))) <invoke make> (= (file-write-date output-file) old-write-date)))
This would be coupled (here's the icky part) with a PERFORM method that does nothing, because by the time it's invoked the make will already have run.
Cheers, r