Fix the Requires() examples by adding a sleep command to the
[scons.git] / doc / user / depends.xml
1 <!--
2
3   __COPYRIGHT__
4
5   Permission is hereby granted, free of charge, to any person obtaining
6   a copy of this software and associated documentation files (the
7   "Software"), to deal in the Software without restriction, including
8   without limitation the rights to use, copy, modify, merge, publish,
9   distribute, sublicense, and/or sell copies of the Software, and to
10   permit persons to whom the Software is furnished to do so, subject to
11   the following conditions:
12
13   The above copyright notice and this permission notice shall be included
14   in all copies or substantial portions of the Software.
15
16   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY
17   KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
18   WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19   NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20   LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21   OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22   WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
23
24 -->
25
26   <para>
27
28   So far we've seen how &SCons; handles one-time builds.
29   But one of the main functions of a build tool like &SCons;
30   is to rebuild only what is necessary
31   when source files change--or, put another way,
32   &SCons; should <emphasis>not</emphasis>
33   waste time rebuilding things that don't need to be rebuilt.
34   You can see this at work simply by re-invoking &SCons;
35   after building our simple &hello; example:
36
37   </para>
38
39   
40
41   <screen>
42      % <userinput>scons -Q</userinput>
43      cc -o hello.o -c hello.c
44      cc -o hello hello.o
45      % <userinput>scons -Q</userinput>
46      scons: `.' is up to date.
47   </screen>
48
49   <para>
50
51   The second time it is executed,
52   &SCons; realizes that the &hello; program
53   is up-to-date with respect to the current &hello_c; source file,
54   and avoids rebuilding it.
55   You can see this more clearly by naming
56   the &hello; program explicitly on the command line:
57
58   </para>
59
60   <screen>
61      % <userinput>scons -Q hello</userinput>
62      cc -o hello.o -c hello.c
63      cc -o hello hello.o
64      % <userinput>scons -Q hello</userinput>
65      scons: `hello' is up to date.
66   </screen>
67
68   <para>
69
70   Note that &SCons; reports <literal>"...is up to date"</literal>
71   only for target files named explicitly on the command line,
72   to avoid cluttering the output.
73
74   </para>
75
76   <section>
77   <title>Deciding When an Input File Has Changed:  the &Decider; Function</title>
78
79     <para>
80
81     Another aspect of avoiding unnecessary rebuilds
82     is the fundamental build tool behavior
83     of <emphasis>rebuilding</emphasis>
84     things when an input file changes,
85     so that the built software is up to date.
86     By default,
87     &SCons; keeps track of this through an
88     MD5 &signature;, or checksum, of the contents of each file,
89     although you can easily configure
90     &SCons; to use the
91     modification times (or time stamps)
92     instead.
93     You can even specify your own Python function
94     for deciding if an input file has changed.
95
96     </para>
97
98     <section>
99     <title>Using MD5 Signatures to Decide if a File Has Changed</title>
100
101       <para>
102
103       By default,
104       &SCons; keeps track of whether a file has changed
105       based on an MD5 checksum of the file's contents,
106       not the file's modification time.
107       This means that you may be surprised by the
108       default &SCons; behavior if you are used to the
109       &Make; convention of forcing
110       a rebuild by updating the file's modification time
111       (using the &touch; command, for example):
112
113       </para>
114
115       <screen>
116          % <userinput>scons -Q hello</userinput>
117          cc -o hello.o -c hello.c
118          cc -o hello hello.o
119          % <userinput>touch hello.c</userinput>
120          % <userinput>scons -Q hello</userinput>
121          scons: `hello' is up to date.
122       </screen>
123
124       <para>
125
126       Even though the file's modification time has changed,
127       &SCons; realizes that the contents of the
128       &hello_c; file have <emphasis>not</emphasis> changed,
129       and therefore that the &hello; program
130       need not be rebuilt.
131       This avoids unnecessary rebuilds when,
132       for example, someone rewrites the
133       contents of a file without making a change.
134       But if the contents of the file really do change,
135       then &SCons; detects the change
136       and rebuilds the program as required:
137
138       </para>
139
140       <screen>
141          % <userinput>scons -Q hello</userinput>
142          cc -o hello.o -c hello.c
143          cc -o hello hello.o
144          % <userinput>edit hello.c</userinput>
145              [CHANGE THE CONTENTS OF hello.c]
146          % <userinput>scons -Q hello</userinput>
147          cc -o hello.o -c hello.c
148          cc -o hello hello.o
149       </screen>
150
151       <para>
152
153       Note that you can, if you wish,
154       specify this default behavior
155       (MD5 signatures) explicitly
156       using the &Decider; function as follows:
157
158       </para>
159
160       <programlisting>
161         Program('hello.c')
162         Decider('MD5')
163       </programlisting>
164
165       <para>
166
167       You can also use the string <literal>'content'</literal>
168       as a synonym for <literal>'MD5'</literal>
169       when calling the &Decider; function.
170
171       </para>
172
173       <section>
174       <title>Ramifications of Using MD5 Signatures</title>
175
176         <para>
177
178         Using MD5 signatures to decide if an input file has changed
179         has one surprising benefit:
180         if a source file has been changed
181         in such a way that the contents of the
182         rebuilt target file(s)
183         will be exactly the same as the last time
184         the file was built,
185         then any "downstream" target files
186         that depend on the rebuilt-but-not-changed target
187         file actually need not be rebuilt.
188
189         </para>
190
191         <para>
192
193         So if, for example,
194         a user were to only change a comment in a &hello_c; file,
195         then the rebuilt &hello_o; file
196         would be exactly the same as the one previously built
197         (assuming the compiler doesn't put any build-specific
198         information in the object file).
199         &SCons; would then realize that it would not
200         need to rebuild the &hello; program as follows:
201
202         </para>
203
204         <screen>
205            % <userinput>scons -Q hello</userinput>
206            cc -o hello.o -c hello.c
207            cc -o hello hello.o
208            % <userinput>edit hello.c</userinput>
209              [CHANGE A COMMENT IN hello.c]
210            % <userinput>scons -Q hello</userinput>
211            cc -o hello.o -c hello.c
212            scons: `hello' is up to date.
213         </screen>
214
215         <para>
216
217         In essence, &SCons;
218         "short-circuits" any dependent builds
219         when it realizes that a target file
220         has been rebuilt to exactly the same file as the last build.
221         This does take some extra processing time
222         to read the contents of the target (&hello_o;) file,
223         but often saves time when the rebuild that was avoided
224         would have been time-consuming and expensive.
225
226         </para>
227
228       </section>
229
230     </section>
231
232     <section>
233     <title>Using Time Stamps to Decide If a File Has Changed</title>
234
235       <para>
236
237       If you prefer, you can
238       configure &SCons; to use the modification time
239       of a file, not the file contents,
240       when deciding if a target needs to be rebuilt.
241       &SCons; gives you two ways to use time stamps
242       to decide if an input file has changed
243       since the last time a target has been built.
244
245       </para>
246
247       <para>
248
249       The most familiar way to use time stamps
250       is the way &Make; does:
251       that is, have &SCons; decide
252       that a target must be rebuilt
253       if a source file's modification time is
254       <emphasis>newer</emphasis>
255       than the target file.
256       To do this, call the &Decider;
257       function as follows:
258
259       </para>
260
261       <programlisting>
262         Program('hello.c')
263         Decider('timestamp-newer')
264       </programlisting>
265
266       <para>
267
268       This makes &SCons; act like &Make;
269       when a file's modification time is updated
270       (using the &touch; command, for example):
271
272       </para>
273
274       <screen>
275          % <userinput>scons -Q hello</userinput>
276          cc -o hello.o -c hello.c
277          cc -o hello hello.o
278          % <userinput>touch hello.c</userinput>
279          % <userinput>scons -Q hello</userinput>
280          cc -o hello.o -c hello.c
281          cc -o hello hello.o
282       </screen>
283
284       <para>
285
286       And, in fact, because this behavior is the same
287       as the behavior of &Make;,
288       you can also use the string <literal>'make'</literal>
289       as a synonym for <literal>'timestamp-newer'</literal>
290       when calling the &Decider; function:
291
292       </para>
293
294       <programlisting>
295         Program('hello.c')
296         Decider('make')
297       </programlisting>
298
299       <para>
300
301       One drawback to using times stamps exactly like &Make;
302       is that if an input file's modification time suddenly
303       becomes <emphasis>older</emphasis> than a target file,
304       the target file will not be rebuilt.
305       This can happen if an old copy of a source file is restored
306       from a backup archive, for example.
307       The contents of the restored file will likely be different
308       than they were the last time a dependent target was built,
309       but the target won't be rebuilt
310       because the modification time of the source file
311       is not newer than the target.
312
313       </para>
314
315       <para>
316
317       Because &SCons; actually stores information
318       about the source files' time stamps whenever a target is built,
319       it can handle this situation by checking for
320       an exact match of the source file time stamp,
321       instead of just whether or not the source file
322       is newer than the target file.
323       To do this, specify the argument
324       <literal>'timestamp-match'</literal>
325       when calling the &Decider; function:
326
327       </para>
328
329       <programlisting>
330         Program('hello.c')
331         Decider('timestamp-match')
332       </programlisting>
333
334       <para>
335
336       When configured this way,
337       &SCons; will rebuild a target whenever
338       a source file's modification time has changed.
339       So if we use the <literal>touch -t</literal>
340       option to change the modification time of
341       &hello_c; to an old date (January 1, 1989),
342       &SCons; will still rebuild the target file:
343
344       </para>
345
346       <screen>
347          % <userinput>scons -Q hello</userinput>
348          cc -o hello.o -c hello.c
349          cc -o hello hello.o
350          % <userinput>touch -t 198901010000 hello.c</userinput>
351          % <userinput>scons -Q hello</userinput>
352          cc -o hello.o -c hello.c
353          cc -o hello hello.o
354       </screen>
355
356       <para>
357
358       In general, the only reason to prefer
359       <literal>timestamp-newer</literal>
360       instead of
361       <literal>timestamp-match</literal>,
362       would be if you have some specific reason
363       to require this &Make;-like behavior of 
364       not rebuilding a target when an otherwise-modified
365       source file is older.
366
367       </para>
368
369     </section>
370
371     <section>
372     <title>Deciding If a File Has Changed Using Both MD Signatures and Time Stamps</title>
373
374       <para>
375
376       As a performance enhancement,
377       &SCons; provides a way to use
378       MD5 checksums of file contents
379       but to read those contents
380       only when the file's timestamp has changed.
381       To do this, call the &Decider;
382       function with <literal>'MD5-timestamp'</literal>
383       argument as follows:
384
385       </para>
386
387       <programlisting>
388         Program('hello.c')
389         Decider('MD5-timestamp')
390       </programlisting>
391
392       <para>
393
394       So configured, &SCons; will still behave like
395       it does when using <literal>Decider('MD5')</literal>:
396
397       </para>
398
399       <!--
400
401       We want to generate the output as follows,
402       but our "surrogate" system for generating the
403       output seems to get this wrong.
404       Just in-line the output for now.
405
406       <scons_output example="MD5-timestamp" os="posix">
407          <scons_output_command>scons -Q hello</scons_output_command>
408          <scons_output_command>touch hello.c</scons_output_command>
409          <scons_output_command>scons -Q hello</scons_output_command>
410        <scons_output_command output="    [CHANGE THE CONTENTS OF hello.c]">edit hello.c</scons_output_command>
411          <scons_output_command>scons -Q hello</scons_output_command>
412       </scons_output>
413
414       -->
415
416       <screen>
417          % <userinput>scons -Q hello</userinput>
418          cc -o hello.o -c hello.c
419          cc -o hello hello.o
420          % <userinput>touch hello.c</userinput>
421          % <userinput>scons -Q hello</userinput>
422          scons: `hello' is up to date.
423          % <userinput>edit hello.c</userinput>
424              [CHANGE THE CONTENTS OF hello.c]
425          % <userinput>scons -Q hello</userinput>
426          cc -o hello.o -c hello.c
427          cc -o hello hello.o
428       </screen>
429
430       <para>
431
432       However, the second call to &SCons; in the above output,
433       when the build is up-to-date,
434       will have been performed by simply looking at the
435       modification time of the &hello_c; file,
436       not by opening it and performing
437       an MD5 checksum calcuation on its contents.
438       This can significantly speed up many up-to-date builds.
439
440       </para>
441
442       <para>
443
444       The only drawback to using
445       <literal>Decider('MD5-timestamp')</literal>
446       is that &SCons; will <emphasis>not</emphasis>
447       rebuild a target file if a source file was modified
448       within one second of the last time &SCons; built the file.
449       While most developers are programming,
450       this isn't a problem in practice,
451       since it's unlikely that someone will have built
452       and then thought quickly enough to make a substantive
453       change to a source file within one second.
454       Certain build scripts or
455       continuous integration tools may, however,
456       rely on the ability to apply changes to files
457       automatically and then rebuild as quickly as possible,
458       in which case use of
459       <literal>Decider('MD5-timestamp')</literal>
460       may not be appropriate.
461
462       </para>
463
464     </section>
465
466     <section>
467     <title>Writing Your Own Custom &Decider; Function</title>
468
469       <para>
470
471       The different string values that we've passed to
472       the &Decider; function are essentially used by &SCons;
473       to pick one of several specific internal functions
474       that implement various ways of deciding if a dependency
475       (usually a source file)
476       has changed since a target file has been built.
477       As it turns out,
478       you can also supply your own function
479       to decide if a dependency has changed.
480
481       </para>
482
483       <para>
484
485       For example, suppose we have an input file
486       that contains a lot of data,
487       in some specific regular format,
488       that is used to rebuild a lot of different target files,
489       but each target file really only depends on
490       one particular section of the input file.
491       We'd like to have each target file depend on
492       only its section of the input file.
493       However, since the input file may contain a lot of data,
494       we want to open the input file only if its timestamp has changed.
495       This could done with a custom
496       &Decider; function that might look something like this:
497
498       </para>
499
500       <programlisting>
501         Program('hello.c')
502         def decide_if_changed(dependency, target, prev_ni):
503             if self.get_timestamp() != prev_ni.timestamp:
504                 dep = str(dependency)
505                 tgt = str(target)
506                 if specific_part_of_file_has_changed(dep, tgt):
507                     return True
508             return False
509         Decider(decide_if_changed)
510       </programlisting>
511
512       <para>
513
514       Note that in the function definition,
515       the <varname>dependency</varname>
516       (input file) is the first argument,
517       and then the &target;.
518       Both of these are passed to the functions as
519       SCons &Node; objects,
520       which we convert to strings using the Python
521       <function>str()</function>.
522
523       </para>
524
525       <para>
526
527       The third argument, <varname>prev_ni</varname>,
528       is an object that holds the
529       signature or timestamp information
530       that was recorded about the dependency
531       the last time the target was built.
532       A <varname>prev_ni</varname> object can hold
533       different information,
534       depending on the type of thing that the
535       <varname>dependency</varname> argument represents.
536       For normal files,
537       the <varname>prev_ni</varname> object
538       has the following attributes:
539
540       </para>
541
542       <variablelist>
543
544         <varlistentry>
545         <term>.csig</term>
546
547         <listitem>
548         <para>
549         The <emphasis>content signature</emphasis>,
550         or MD5 checksum, of the contents of the
551         <varname>dependency</varname>
552         file the list time the &target; was built.
553         </para>
554         </listitem>
555
556         </varlistentry>
557
558         <varlistentry>
559         <term>.size</term>
560
561         <listitem>
562         <para>
563         The size in bytes of the <varname>dependency</varname>
564         file the list time the target was built.
565         </para>
566         </listitem>
567
568         </varlistentry>
569
570         <varlistentry>
571         <term>.timestamp</term>
572
573         <listitem>
574         <para>
575         The modification time of the <varname>dependency</varname>
576         file the list time the &target; was built.
577         </para>
578         </listitem>
579
580         </varlistentry>
581
582       </variablelist>
583
584       <para>
585
586       Note that ignoring some of the arguments
587       in your custom &Decider; function
588       is a perfectly normal thing to do,
589       if they don't impact the way you want to
590       decide if the dependency file has changed.
591
592       </para>
593
594     </section>
595
596     <section>
597     <title>Mixing Different Ways of Deciding If a File Has Changed</title>
598
599       <para>
600
601       The previous examples have all demonstrated calling
602       the global &Decider; function
603       to configure all dependency decisions that &SCons; makes.
604       Sometimes, however, you want to be able to configure
605       different decision-making for different targets.
606       When that's necessary, you can use the
607       <function>env.Decider</function>
608       method to affect only the configuration
609       decisions for targets built with a
610       specific construction environment.
611
612       </para>
613
614       <para>
615
616       For example, if we arbitrarily want to build
617       one program using MD5 checkums
618       and another using file modification times
619       from the same source
620       we might configure it this way:
621
622       </para>
623
624       <programlisting>
625         env1 = Environment(CPPPATH = ['.'])
626         env2 = env1.Clone()
627         env2.Decider('timestamp-match')
628         env1.Program('prog-MD5', 'program1.c')
629         env2.Program('prog-timestamp', 'program2.c')
630       </programlisting>
631
632       <para>
633
634       If both of the programs include the same
635       <filename>inc.h</filename> file,
636       then updating the modification time of
637       <filename>inc.h</filename>
638       (using the &touch; command)
639       will cause only <filename>prog-timestamp</filename>
640       to be rebuilt:
641
642       </para>
643
644       <screen>
645          % <userinput>scons -Q</userinput>
646          cc -o program1.o -c -I. program1.c
647          cc -o prog-MD5 program1.o
648          cc -o program2.o -c -I. program2.c
649          cc -o prog-timestamp program2.o
650          % <userinput>touch inc.h</userinput>
651          % <userinput>scons -Q</userinput>
652          cc -o program2.o -c -I. program2.c
653          cc -o prog-timestamp program2.o
654       </screen>
655
656     </section>
657
658   </section>
659
660   <section>
661   <title>Older Functions for Deciding When an Input File Has Changed</title>
662
663     <para>
664
665     &SCons; still supports two functions that used to be the
666     primary methods for configuring the
667     decision about whether or not an input file has changed.
668     Although they're not officially deprecated yet,
669     their use is discouraged,
670     mainly because they rely on a somewhat
671     confusing distinction between how
672     source files and target files are handled.
673     These functions are documented here mainly in case you
674     encounter them in existing &SConscript; files.
675
676     </para>
677   
678     <section>
679     <title>The &SourceSignatures; Function</title>
680
681       <para>
682
683       The &SourceSignatures; function is fairly straightforward,
684       and supports two different argument values
685       to configure whether source file changes should be decided
686       using MD5 signatures:
687
688       </para>
689
690       <programlisting>
691         Program('hello.c')
692         SourceSignatures('MD5')
693       </programlisting>
694
695       <para>
696
697       Or using time stamps:
698
699       </para>
700
701       <programlisting>
702         Program('hello.c')
703         SourceSignatures('timestamp')
704       </programlisting>
705
706       <para>
707
708       These are roughly equivalent to specifying
709       <function>Decider('MD5')</function>
710       or
711       <function>Decider('timestamp-match')</function>,
712       respectively,
713       although it only affects how SCons makes
714       decisions about dependencies on
715       <emphasis>source</emphasis> files--that is,
716       files that are not built from any other files.
717
718       </para>
719
720     </section>
721
722     <section>
723     <title>The &TargetSignatures; Function</title>
724
725       <para>
726
727       The &TargetSignatures; function
728       specifies how &SCons; decides
729       when a target file has changed
730       <emphasis>when it is used as a
731       dependency of (input to) another target</emphasis>--that is,
732       the &TargetSignatures; function configures
733       how the signatures of "intermediate" target files
734       are used when deciding if a "downstream" target file
735       must be rebuilt.
736       <footnote><para>
737       This easily-overlooked distinction between
738       how &SCons; decides if the target itself must be rebuilt
739       and how the target is then used to decide if a different
740       target must be rebuilt is one of the confusing
741       things that has led to the &TargetSignatures;
742       and &SourceSignatures; functions being
743       replaced by the simpler &Decider; function.
744       </para></footnote>
745
746       </para>
747
748       <para>
749
750       The &TargetSignatures; function supports the same
751       <literal>'MD5'</literal> and <literal>'timestamp'</literal>
752       argument values that are supported by the &SourceSignatures;,
753       with the same meanings, but applied to target files.
754       That is, in the example:
755
756       </para>
757
758       <programlisting>
759         Program('hello.c')
760         TargetSignatures('MD5')
761       </programlisting>
762
763       <para>
764
765       The MD5 checksum of the &hello_o; target file
766       will be used to decide if it has changed since the last
767       time the "downstream" &hello; target file was built.
768       And in the example:
769       
770       </para>
771
772       <programlisting>
773         Program('hello.c')
774         TargetSignatures('timestamp')
775       </programlisting>
776
777       <para>
778
779       The modification time of the &hello_o; target file
780       will be used to decide if it has changed since the last
781       time the "downstream" &hello; target file was built.
782
783       </para>
784
785       <para>
786
787       The &TargetSignatures; function supports
788       two additional argument values:
789       <literal>'source'</literal> and <literal>'build'</literal>.
790       The <literal>'source'</literal> argument
791       specifies that decisions involving
792       whether target files have changed
793       since a previous build
794       should use the same behavior
795       for the decisions configured for source files
796       (using the &SourceSignatures; function).
797       So in the example:
798
799       </para>
800
801       <programlisting>
802         Program('hello.c')
803         TargetSignatures('source')
804         SourceSignatures('timestamp')
805       </programlisting>
806
807       <para>
808
809       All files, both targets and sources,
810       will use modification times
811       when deciding if an input file
812       has changed since the last
813       time a target was built.
814
815       </para>
816
817       <para>
818
819       Lastly, the <literal>'build'</literal> argument
820       specifies that &SCons; should examine
821       the build status of a target file
822       and always rebuild a "downstream" target
823       if the target file was itself rebuilt,
824       without re-examining the contents or timestamp
825       of the newly-built target file.
826       If the target file was not rebuilt during
827       this &scons; invocation,
828       then the target file will be examined
829       the same way as configured by
830       the &SourceSignature; call
831       to decide if it has changed.
832
833       </para>
834
835       <para>
836
837       This mimics the behavior of
838       <literal>build signatures</literal>
839       in earlier versions of &SCons;.
840       A &buildsignature; re-combined
841       signatures of all the input files
842       that went into making the target file,
843       so that the target file itself
844       did not need to have its contents read
845       to compute an MD5 signature.
846       This can improve performance for some configurations,
847       but is generally not as effective as using
848       <literal>Decider('MD5-timestamp')</literal>.
849
850       </para>
851
852     </section>
853
854   </section>
855
856   <section>
857   <title>Implicit Dependencies:  The &cv-CPPPATH; Construction Variable</title>
858
859     <para>
860
861     Now suppose that our "Hello, World!" program
862     actually has an <literal>#include</literal> line
863     to include the &hello_h; file in the compilation:
864
865     </para>
866
867     <programlisting>
868        #include &lt;hello.h&gt;
869        int
870        main()
871        {
872            printf("Hello, %s!\n", string);
873        }
874     </programlisting>
875
876     <para>
877
878     And, for completeness, the &hello_h; file looks like this:
879
880     </para>
881
882     
883     <programlisting>
884        #define string    "world"
885       </programlisting>
886
887     <para>
888
889     In this case, we want &SCons; to recognize that,
890     if the contents of the &hello_h; file change,
891     the &hello; program must be recompiled.
892     To do this, we need to modify the
893     &SConstruct; file like so:
894
895     </para>
896
897     
898     <programlisting>
899        Program('hello.c', CPPPATH = '.')
900       </programlisting>
901
902     <para>
903
904     The &cv-link-CPPPATH; value
905     tells &SCons; to look in the current directory
906     (<literal>'.'</literal>)
907     for any files included by C source files
908     (<filename>.c</filename> or <filename>.h</filename> files).
909     With this assignment in the &SConstruct; file:
910
911     </para>
912
913     <screen>
914        % <userinput>scons -Q hello</userinput>
915        cc -o hello.o -c -I. hello.c
916        cc -o hello hello.o
917        % <userinput>scons -Q hello</userinput>
918        scons: `hello' is up to date.
919        % <userinput>edit hello.h</userinput>
920            [CHANGE THE CONTENTS OF hello.h]
921        % <userinput>scons -Q hello</userinput>
922        cc -o hello.o -c -I. hello.c
923        cc -o hello hello.o
924     </screen>
925
926     <para>
927
928     First, notice that &SCons;
929     added the <literal>-I.</literal> argument
930     from the &cv-CPPPATH; variable
931     so that the compilation would find the
932     &hello_h; file in the local directory.
933
934     </para>
935
936     <para>
937
938     Second, realize that &SCons; knows that the &hello;
939     program must be rebuilt
940     because it scans the contents of
941     the &hello_c; file
942     for the <literal>#include</literal> lines that indicate
943     another file is being included in the compilation.
944     &SCons; records these as
945     <emphasis>implicit dependencies</emphasis>
946     of the target file,
947     Consequently,
948     when the &hello_h; file changes,
949     &SCons; realizes that the &hello_c; file includes it,
950     and rebuilds the resulting &hello; program
951     that depends on both the &hello_c; and &hello_h; files.
952
953     </para>
954
955     <para>
956
957     Like the &cv-link-LIBPATH; variable,
958     the &cv-CPPPATH; variable
959     may be a list of directories,
960     or a string separated by
961     the system-specific path separation character
962     (':' on POSIX/Linux, ';' on Windows).
963     Either way, &SCons; creates the
964     right command-line options
965     so that the following example:
966
967     </para>
968
969     <programlisting>
970        Program('hello.c', CPPPATH = ['include', '/home/project/inc'])
971     </programlisting>
972
973     <para>
974
975     Will look like this on POSIX or Linux:
976
977     </para>
978
979     <screen>
980        % <userinput>scons -Q hello</userinput>
981        cc -o hello.o -c -Iinclude -I/home/project/inc hello.c
982        cc -o hello hello.o
983     </screen>
984
985     <para>
986
987     And like this on Windows:
988
989     </para>
990
991     <screen>
992        C:\><userinput>scons -Q hello.exe</userinput>
993        cl /Fohello.obj /c hello.c /nologo /Iinclude /I\home\project\inc
994        link /nologo /OUT:hello.exe hello.obj
995     </screen>
996
997   </section>
998
999   <section>
1000   <title>Caching Implicit Dependencies</title>
1001
1002     <para>
1003
1004     Scanning each file for <literal>#include</literal> lines
1005     does take some extra processing time.
1006     When you're doing a full build of a large system,
1007     the scanning time is usually a very small percentage
1008     of the overall time spent on the build.
1009     You're most likely to notice the scanning time,
1010     however, when you <emphasis>rebuild</emphasis>
1011     all or part of a large system:
1012     &SCons; will likely take some extra time to "think about"
1013     what must be built before it issues the
1014     first build command
1015     (or decides that everything is up to date
1016     and nothing must be rebuilt).
1017
1018  <!--
1019  Isn't this expensive? The answer is, it depends. If you do a full build of a
1020  large system, the scanning time is insignificant. If you do a rebuild of a
1021  large system, then Cons will spend a fair amount of time thinking about it
1022  before it decides that nothing has to be done (although not necessarily more
1023  time than make!). The good news is that Cons makes it very easy to
1024  intelligently subset your build, when you are working on localized changes.
1025  -->
1026
1027     </para>
1028
1029     <para>
1030
1031     In practice, having &SCons; scan files saves time
1032     relative to the amount of potential time
1033     lost to tracking down subtle problems
1034     introduced by incorrect dependencies.
1035     Nevertheless, the "waiting time"
1036     while &SCons; scans files can annoy
1037     individual developers waiting for their builds to finish.
1038     Consequently, &SCons; lets you cache
1039     the implicit dependencies
1040     that its scanners find,
1041     for use by later builds.
1042     You can do this by specifying the
1043     &implicit-cache; option on the command line:
1044
1045     </para>
1046
1047     <screen>
1048        % <userinput>scons -Q --implicit-cache hello</userinput>
1049        cc -o hello.o -c hello.c
1050        cc -o hello hello.o
1051        % <userinput>scons -Q hello</userinput>
1052        scons: `hello' is up to date.
1053     </screen>
1054
1055     <para>
1056
1057     If you don't want to specify &implicit-cache;
1058     on the command line each time,
1059     you can make it the default behavior for your build
1060     by setting the &implicit_cache; option
1061     in an &SConscript; file:
1062
1063     </para>
1064
1065     <programlisting>
1066        SetOption('implicit_cache', 1)
1067     </programlisting>
1068
1069     <para>
1070
1071     &SCons; does not cache implicit dependencies like this by default
1072     because the &implicit-cache; causes &SCons; to simply use the implicit
1073     dependencies stored during the last run, without any checking
1074     for whether or not those dependencies are still correct.
1075     Specifically, this means &implicit-cache; instructs &SCons;
1076     to <emphasis>not</emphasis> rebuild "correctly" in the
1077     following cases:
1078
1079
1080     </para>
1081
1082     <itemizedlist>
1083
1084       <listitem>
1085         <para>
1086
1087         When &implicit-cache; is used, &SCons; will ignore any changes that
1088         may have been made to search paths
1089         (like &cv-CPPPATH; or &cv-LIBPATH;,).
1090         This can lead to &SCons; not rebuilding a file if a change to
1091         &cv-CPPPATH; would normally cause a different, same-named file from
1092         a different directory to be used.
1093
1094         </para>
1095       </listitem>
1096
1097       <listitem>
1098         <para>
1099
1100         When &implicit-cache; is used, &SCons; will not detect if a
1101         same-named file has been added to a directory that is earlier in
1102         the search path than the directory in which the file was found
1103         last time.
1104
1105         </para>
1106       </listitem>
1107
1108     </itemizedlist>
1109
1110     <section>
1111     <title>The &implicit-deps-changed; Option</title>
1112
1113       <para>
1114
1115       When using cached implicit dependencies,
1116       sometimes you want to "start fresh"
1117       and have &SCons; re-scan the files
1118       for which it previously cached the dependencies.
1119       For example,
1120       if you have recently installed a new version of
1121       external code that you use for compilation,
1122       the external header files will have changed
1123       and the previously-cached implicit dependencies
1124       will be out of date.
1125       You can update them by
1126       running &SCons; with the &implicit-deps-changed; option:
1127
1128       </para>
1129
1130       <screen>
1131          % <userinput>scons -Q --implicit-deps-changed hello</userinput>
1132          cc -o hello.o -c hello.c
1133          cc -o hello hello.o
1134          % <userinput>scons -Q hello</userinput>
1135          scons: `hello' is up to date.
1136       </screen>
1137
1138       <para>
1139
1140       In this case, &SCons; will re-scan all of the implicit dependencies
1141       and cache updated copies of the information.
1142
1143       </para>
1144
1145     </section>
1146
1147     <section>
1148     <title>The &implicit-deps-unchanged; Option</title>
1149
1150       <para>
1151
1152       By default when caching dependencies,
1153       &SCons; notices when a file has been modified
1154       and re-scans the file for any updated
1155       implicit dependency information.
1156       Sometimes, however, you may want
1157       to force &SCons; to use the cached implicit dependencies,
1158       even if the source files changed.
1159       This can speed up a build for example,
1160       when you have changed your source files
1161       but know that you haven't changed
1162       any <literal>#include</literal> lines.
1163       In this case,
1164       you can use the &implicit-deps-unchanged; option:
1165
1166       </para>
1167
1168       <screen>
1169          % <userinput>scons -Q --implicit-deps-unchanged hello</userinput>
1170          cc -o hello.o -c hello.c
1171          cc -o hello hello.o
1172          % <userinput>scons -Q hello</userinput>
1173          scons: `hello' is up to date.
1174       </screen>
1175
1176       <para>
1177
1178       In this case,
1179       &SCons; will assume that the cached implicit
1180       dependencies are correct and
1181       will not bother to re-scan changed files.
1182       For typical builds after small,
1183       incremental changes to source files,
1184       the savings may not be very big,
1185       but sometimes every bit of
1186       improved performance counts.
1187
1188       </para>
1189
1190     </section>
1191
1192     <!--
1193
1194     <section>
1195     <title>XXX max drift</title>
1196
1197       XXX SetOption('max_drift')
1198
1199     </section>
1200
1201     -->
1202
1203   </section>
1204
1205   <section>
1206   <title>Explicit Dependencies:  the &Depends; Function</title>
1207
1208     <para>
1209
1210     Sometimes a file depends on another file
1211     that is not detected by an &SCons; scanner.
1212     For this situation,
1213     &SCons; allows you to specific explicitly that one file
1214     depends on another file,
1215     and must be rebuilt whenever that file changes.
1216     This is specified using the &Depends; method:
1217
1218     </para>
1219
1220     <programlisting>
1221        hello = Program('hello.c')
1222        Depends(hello, 'other_file')
1223     </programlisting>
1224
1225     <!-- XXX mention that you can use arrays for target and source? -->
1226
1227     <screen>
1228        % <userinput>scons -Q hello</userinput>
1229        cc -c hello.c -o hello.o
1230        cc -o hello hello.o
1231        % <userinput>scons -Q hello</userinput>
1232        scons: `hello' is up to date.
1233        % <userinput>edit other_file</userinput>
1234            [CHANGE THE CONTENTS OF other_file]
1235        % <userinput>scons -Q hello</userinput>
1236        cc -c hello.c -o hello.o
1237        cc -o hello hello.o
1238     </screen>
1239
1240     <para>
1241
1242     Note that the dependency
1243     (the second argument to &Depends;)
1244     may also be a list of Node objects
1245     (for example, as returned by a call to a Builder):
1246
1247     </para>
1248
1249     <programlisting>
1250        hello = Program('hello.c')
1251        goodbye = Program('goodbye.c')
1252        Depends(hello, goodbye)
1253     </programlisting>
1254
1255     <para>
1256
1257     in which case the dependency or dependencies
1258     will be built before the target(s):
1259
1260     </para>
1261
1262     <screen>
1263        % <userinput>scons -Q hello</userinput>
1264        cc -c goodbye.c -o goodbye.o
1265        cc -o goodbye goodbye.o
1266        cc -c hello.c -o hello.o
1267        cc -o hello hello.o
1268     </screen>
1269
1270   </section>
1271
1272   <section>
1273   <title>Dependencies From External Files:  the &ParseDepends;
1274   Function</title>
1275
1276     <para>
1277
1278     &SCons; has built-in scanners for a number of languages. Sometimes
1279     these scanners fail to extract certain implicit dependencies due
1280     to limitations of the scanner implementation.
1281
1282     </para>
1283
1284     <para>
1285
1286     The following example illustrates a case where the built-in C
1287     scanner is unable to extract the implicit dependency on a header
1288     file.
1289
1290     </para>
1291
1292     <programlisting>
1293       #define FOO_HEADER &lt;foo.h&gt;
1294       #include FOO_HEADER
1295
1296       int main() {
1297           return FOO;
1298       }
1299     </programlisting>
1300
1301     <screen>
1302       % <userinput>scons -Q</userinput>
1303       cc -o hello.o -c -I. hello.c
1304       cc -o hello hello.o
1305       % <userinput>edit foo.h</userinput>
1306          [CHANGE CONTENTS OF foo.h]
1307       % <userinput>scons -Q</userinput>
1308       scons: `.' is up to date.
1309     </screen>
1310
1311     <para>
1312
1313     Apparently, the scanner does not know about the header dependency.
1314     Being not a full-fledged C preprocessor, the scanner does not
1315     expand the macro.
1316
1317     </para>
1318
1319     <para>
1320
1321     In these cases, you may also use the compiler to extract the
1322     implicit dependencies. &ParseDepends; can parse the contents of
1323     the compiler output in the style of &Make;, and explicitly
1324     establish all of the listed dependencies.
1325
1326     </para>
1327
1328     <para>
1329
1330     The following example uses &ParseDepends; to process a compiler
1331     generated dependency file which is generated as a side effect
1332     during compilation of the object file:
1333
1334     </para>
1335
1336     <!-- XXX The ParseDepends example below fakes proper working by a
1337     priori specification of the dependency file. The produced hello.d
1338     file is not found (or used) for unknown reasons. -->
1339
1340     <programlisting>
1341       obj = Object('hello.c', CCFLAGS='-MD -MF hello.d', CPPPATH='.')
1342       SideEffect('hello.d', obj)
1343       ParseDepends('hello.d')
1344       Program('hello', obj)
1345     </programlisting>
1346
1347     <screen>
1348       % <userinput>scons -Q</userinput>
1349       cc -o hello.o -c -MD -MF hello.d -I. hello.c
1350       cc -o hello hello.o
1351       % <userinput>edit foo.h</userinput>
1352          [CHANGE CONTENTS OF foo.h]
1353       % <userinput>scons -Q</userinput>
1354       cc -o hello.o -c -MD -MF hello.d -I. hello.c
1355     </screen>
1356
1357     <para>
1358
1359     Parsing dependencies from a compiler-generated
1360     <filename>.d</filename> file has a chicken-and-egg problem, that
1361     causes unnecessary rebuilds:
1362
1363     </para>
1364
1365     
1366
1367     <!--
1368     <scons_output example="parsedeprebuild" os="posix">
1369       <scons_output_command>scons -Q</scons_output_command>
1370       <scons_output_command>scons -Q</scons_output_command>
1371       <scons_output_command>scons -Q</scons_output_command>
1372     </scons_output>
1373     -->
1374
1375     <screen>
1376       % <userinput>scons -Q</userinput>
1377       cc -o hello.o -c -MD -MF hello.d -I. hello.c
1378       cc -o hello hello.o
1379       % <userinput>scons -Q --debug=explain</userinput>
1380       scons: rebuilding `hello.o' because `foo.h' is a new dependency
1381       cc -o hello.o -c -MD -MF hello.d -I. hello.c
1382       % <userinput>scons -Q</userinput>
1383       scons: `.' is up to date.
1384     </screen>
1385
1386     <para>
1387
1388     In the first pass, the dependency file is generated while the
1389     object file is compiled. At that time, &SCons; does not know about
1390     the dependency on <filename>foo.h</filename>. In the second pass,
1391     the object file is regenerated because <filename>foo.h</filename>
1392     is detected as a new dependency.
1393
1394     </para>
1395
1396     <para>
1397
1398     &ParseDepends; immediately reads the specified file at invocation
1399     time and just returns if the file does not exist. A dependency
1400     file generated during the build process is not automatically
1401     parsed again. Hence, the compiler-extracted dependencies are not
1402     stored in the signature database during the same build pass. This
1403     limitation of &ParseDepends; leads to unnecessary recompilations.
1404     Therefore, &ParseDepends; should only be used if scanners are not
1405     available for the employed language or not powerful enough for the
1406     specific task.
1407
1408     </para>
1409
1410   </section>
1411
1412   <section>
1413   <title>Ignoring Dependencies:  the &Ignore; Function</title>
1414
1415     <para>
1416
1417     Sometimes it makes sense
1418     to not rebuild a program,
1419     even if a dependency file changes.
1420     In this case,
1421     you would tell &SCons; specifically
1422     to ignore a dependency as follows:
1423
1424     </para>
1425
1426     <programlisting>
1427       hello_obj=Object('hello.c')
1428       hello = Program(hello_obj)
1429       Ignore(hello_obj, 'hello.h')
1430     </programlisting>
1431
1432     <!-- XXX mention that you can use lists for target and source? -->
1433
1434     <!--
1435     <scons_output example="ignore">
1436       <scons_output_command>scons -Q hello</scons_output_command>
1437       <scons_output_command>scons -Q hello</scons_output_command>
1438       <scons_output_command output="    [CHANGE THE CONTENTS OF hello.h]">edit hello.h</scons_output_command>
1439       <scons_output_command>scons -Q hello</scons_output_command>
1440       XXX THIS EXAMPLE SHOULD BE UP-TO-DATE! XXX
1441     </scons_output>
1442     -->
1443
1444     <screen>
1445       % <userinput>scons -Q hello</userinput>
1446       cc -c -o hello.o hello.c
1447       cc -o hello hello.o
1448       % <userinput>scons -Q hello</userinput>
1449       scons: `hello' is up to date.
1450       % <userinput>edit hello.h</userinput>
1451         [CHANGE THE CONTENTS OF hello.h]
1452       % <userinput>scons -Q hello</userinput>
1453       scons: `hello' is up to date.
1454     </screen>
1455
1456     <para>
1457
1458     Now, the above example is a little contrived,
1459     because it's hard to imagine a real-world situation
1460     where you wouldn't want to rebuild &hello;
1461     if the &hello_h; file changed.
1462     A more realistic example
1463     might be if the &hello;
1464     program is being built in a
1465     directory that is shared between multiple systems
1466     that have different copies of the
1467     &stdio_h; include file.
1468     In that case,
1469     &SCons; would notice the differences between
1470     the different systems' copies of &stdio_h;
1471     and would rebuild &hello;
1472     each time you change systems.
1473     You could avoid these rebuilds as follows:
1474
1475     </para>
1476
1477     <programlisting>
1478        hello = Program('hello.c', CPPPATH=['/usr/include'])
1479        Ignore(hello, '/usr/include/stdio.h')
1480     </programlisting>
1481
1482     <para>
1483     &Ignore; can also be used to prevent a generated file from being built 
1484     by default. This is due to the fact that directories depend on 
1485     their contents.  So to ignore a generated file from the default build, 
1486     you specify that the directory should ignore the generated file.
1487     Note that the file will still be built if the user specifically 
1488     requests the target on scons command line, or if the file is
1489     a dependency of another file which is requested and/or is built
1490     by default.
1491     </para>
1492
1493     <programlisting>
1494       hello_obj=Object('hello.c')
1495       hello = Program(hello_obj)
1496       Ignore('.',[hello,hello_obj])
1497     </programlisting>
1498
1499     <screen>
1500       % <userinput>scons -Q</userinput>
1501       scons: `.' is up to date.
1502       % <userinput>scons -Q hello</userinput>
1503       cc -o hello.o -c hello.c
1504       cc -o hello hello.o
1505       % <userinput>scons -Q hello</userinput>
1506       scons: `hello' is up to date.
1507     </screen>
1508   </section>
1509
1510   <section>
1511   <title>Order-Only Dependencies:  the &Requires; Function</title>
1512
1513     <para>
1514
1515     Occasionally,
1516     it may be useful to specify that a certain
1517     file or directory must, if necessary,
1518     be built or created before some other target is built,
1519     but that changes to that file or directory
1520     do <emphasis>not</emphasis>
1521     require that the target itself be rebuilt.
1522     Such a relationship is called an
1523     <emphasis>order-only dependency</emphasis>
1524     because it only affects the order in which
1525     things must be built--the dependency before the target--but
1526     it is not a strict dependency relationship
1527     because the target should not
1528     change in response to changes in the dependent file.
1529
1530     </para>
1531
1532     <para>
1533
1534     For example, suppose that you want to create a file
1535     every time you run a build
1536     that identifies the time the build was performed,
1537     the version number, etc.,
1538     and which is included in every program that you build.
1539     The version file's contents will change every build.
1540     If you specify a normal dependency relationship,
1541     then every program that depends on
1542     that file would be rebuilt every time you ran &SCons;.
1543     For example, we could use some Python code in
1544     a &SConstruct; file to create a new <filename>version.c</filename> file
1545     with a string containing the current date every time
1546     we run &SCons;,
1547     and then link a program with the resulting object file
1548     by listing <filename>version.c</filename> in the sources:
1549
1550     </para>
1551
1552     <programlisting>
1553       import time
1554
1555       version_c_text = """
1556       char *date = "%s";
1557       """ % time.ctime(time.time())
1558       open('version.c', 'w').write(version_c_text)
1559
1560       hello = Program(['hello.c', 'version.c'])
1561     </programlisting>
1562
1563     <para>
1564
1565     If we list <filename>version.c</filename> as an actual source file,
1566     though, then the <filename>version.o</filename> file
1567     will get rebuilt every time we run &SCons;
1568     (because the &SConstruct; file itself changes
1569     the contents of <filename>version.c</filename>)
1570     and the <filename>hello</filename> executable
1571     will get re-linked every time
1572     (because the <filename>version.o</filename> file changes):
1573
1574     </para>
1575
1576     <screen>
1577       % <userinput>scons -Q hello</userinput>
1578       cc -o hello.o -c hello.c
1579       cc -o version.o -c version.c
1580       cc -o hello hello.o version.o
1581       % <userinput>sleep 1</userinput>
1582       % <userinput>scons -Q hello</userinput>
1583       cc -o version.o -c version.c
1584       cc -o hello hello.o version.o
1585       % <userinput>sleep 1</userinput>
1586       % <userinput>scons -Q hello</userinput>
1587       cc -o version.o -c version.c
1588       cc -o hello hello.o version.o
1589     </screen>
1590
1591     <para>
1592
1593     (Note that for the above example to work,
1594     we &sleep; for one second in between each run,
1595     so that the &SConstruct; file will create a
1596     <filename>version.c</filename> file with a time string
1597     that's one second later than the previous run.)
1598
1599     </para>
1600
1601     <para>
1602
1603     One solution is to use the &Requires; function
1604     to specify that the <filename>version.o</filename>
1605     must be rebuilt before it is used by the link step,
1606     but that changes to <filename>version.o</filename>
1607     should not actually cause the <filename>hello</filename>
1608     executable to be re-linked:
1609
1610     </para>
1611
1612     <programlisting>
1613       import time
1614
1615       version_c_text = """
1616       char *date = "%s";
1617       """ % time.ctime(time.time())
1618       open('version.c', 'w').write(version_c_text)
1619
1620       version_obj = Object('version.c')
1621
1622       hello = Program('hello.c',
1623                       LINKFLAGS = str(version_obj[0]))
1624
1625       Requires(hello, version_obj)
1626     </programlisting>
1627
1628     <para>
1629
1630     Notice that because we can no longer list <filename>version.c</filename>
1631     as one of the sources for the <filename>hello</filename> program,
1632     we have to find some other way to get it into the link command line.
1633     For this example, we're cheating a bit and stuffing the
1634     object file name (extracted from <literal>version_obj</literal>
1635     list returned by the &b-Object; call)
1636     into the &cv-link-LINKFLAGS; variable,
1637     because &cv-LINKFLAGS; is already included
1638     in the &cv-link-LINKCOM; command line.
1639
1640     </para>
1641
1642     <para>
1643
1644     With these changes,
1645     we get the desired behavior of only
1646     re-linking the <filename>hello</filename> executable
1647     when the <filename>hello.c</filename> has changed,
1648     even though the <filename>version.o</filename> is rebuilt
1649     (because the &SConstruct; file still changes the
1650     <filename>version.c</filename> contents directly each run):
1651
1652     </para>
1653
1654     <screen>
1655       % <userinput>scons -Q hello</userinput>
1656       cc -o version.o -c version.c
1657       cc -o hello.o -c hello.c
1658       cc -o hello version.o hello.o
1659       % <userinput>sleep 1</userinput>
1660       % <userinput>scons -Q hello</userinput>
1661       cc -o version.o -c version.c
1662       scons: `hello' is up to date.
1663       % <userinput>sleep 1</userinput>
1664       % <userinput>edit hello.c</userinput>
1665           [CHANGE THE CONTENTS OF hello.c]
1666       % <userinput>scons -Q hello</userinput>
1667       cc -o version.o -c version.c
1668       cc -o hello.o -c hello.c
1669       cc -o hello version.o hello.o
1670       % <userinput>sleep 1</userinput>
1671       % <userinput>scons -Q hello</userinput>
1672       cc -o version.o -c version.c
1673       scons: `hello' is up to date.
1674     </screen>
1675
1676   </section>
1677
1678   <section>
1679   <title>The &AlwaysBuild; Function</title>
1680
1681     <para>
1682
1683     How &SCons; handles dependencies can also be affected
1684     by the &AlwaysBuild; method.
1685     When a file is passed to the &AlwaysBuild; method,
1686     like so:
1687
1688     </para>
1689
1690     <programlisting>
1691       hello = Program('hello.c')
1692       AlwaysBuild(hello)
1693     </programlisting>
1694
1695     <para>
1696
1697     Then the specified target file (&hello; in our example)
1698     will always be considered out-of-date and
1699     rebuilt whenever that target file is evaluated
1700     while walking the dependency graph:
1701
1702     </para>
1703
1704     <screen>
1705       % <userinput>scons -Q</userinput>
1706       cc -o hello.o -c hello.c
1707       cc -o hello hello.o
1708       % <userinput>scons -Q</userinput>
1709       cc -o hello hello.o
1710     </screen>
1711
1712     <para>
1713
1714     The &AlwaysBuild; function has a somewhat misleading name,
1715     because it does not actually mean the target file will
1716     be rebuilt every single time &SCons; is invoked.
1717     Instead, it means that the target will, in fact,
1718     be rebuilt whenever the target file is encountered
1719     while evaluating the targets specified on
1720     the command line (and their dependencies).
1721     So specifying some other target on the command line,
1722     a target that does <emphasis>not</emphasis>
1723     itself depend on the &AlwaysBuild; target,
1724     will still be rebuilt only if it's out-of-date
1725     with respect to its dependencies:
1726
1727     </para>
1728
1729     <screen>
1730       % <userinput>scons -Q</userinput>
1731       cc -o hello.o -c hello.c
1732       cc -o hello hello.o
1733       % <userinput>scons -Q hello.o</userinput>
1734       scons: `hello.o' is up to date.
1735     </screen>
1736
1737     <!--
1738
1739       XXX AlwaysBuild() and Alias Nodes
1740
1741       XXX AlwaysBuild() and Dir Nodes
1742
1743       XXX AlwaysBuild() with no sources
1744
1745     -->
1746
1747   </section>
1748
1749   <!--
1750
1751   <section>
1752   <title>The &Salt; Method</title>
1753
1754     <para>
1755
1756     XXX Salt() (are we going to implement this ?)
1757
1758         original Cons classic POD documentation:
1759
1760 =head2 The C<Salt> method
1761
1762 The C<Salt> method adds a constant value to the signature calculation
1763 for every derived file.  It is invoked as follows:
1764
1765   Salt $string;
1766
1767 Changing the Salt value will force a complete rebuild of every derived
1768 file.  This can be used to force rebuilds in certain desired
1769 circumstances.  For example,
1770
1771   Salt `uname -s`;
1772
1773 Would force a complete rebuild of every derived file whenever the
1774 operating system on which the build is performed (as reported by C<uname
1775 -s>) changes.
1776
1777     </para>
1778
1779   </section>
1780
1781   -->