@@ -283,7 +283,7 @@ pub fn prepare_target<'a, 'cfg>(
283
283
// "consider everything a dependency mode" and then we switch to "deps
284
284
// are explicitly specified" mode.
285
285
//
286
- // To handlet his movement we need to regenerate the `local` field of a
286
+ // To handle this movement we need to regenerate the `local` field of a
287
287
// build script's fingerprint after it's executed. We do this by
288
288
// using the `build_script_local_fingerprints` function which returns a
289
289
// thunk we can invoke on a foreign thread to calculate this.
@@ -378,7 +378,7 @@ pub struct Fingerprint {
378
378
local : Vec < LocalFingerprint > ,
379
379
/// Cached hash of the `Fingerprint` struct. Used to improve performance
380
380
/// for hashing.
381
- #[ serde( skip_serializing , skip_deserializing ) ]
381
+ #[ serde( skip ) ]
382
382
memoized_hash : Mutex < Option < u64 > > ,
383
383
/// RUSTFLAGS/RUSTDOCFLAGS environment variable value (or config value).
384
384
rustflags : Vec < String > ,
@@ -388,13 +388,13 @@ pub struct Fingerprint {
388
388
metadata : u64 ,
389
389
/// Description of whether the filesystem status for this unit is up to date
390
390
/// or should be considered stale.
391
- #[ serde( skip_serializing , skip_deserializing ) ]
391
+ #[ serde( skip ) ]
392
392
fs_status : FsStatus ,
393
393
/// Files, relative to `target_root`, that are produced by the step that
394
394
/// this `Fingerprint` represents. This is used to detect when the whole
395
395
/// fingerprint is out of date if this is missing, or if previous
396
396
/// fingerprints output files are regenerated and look newer than this one.
397
- #[ serde( skip_serializing , skip_deserializing ) ]
397
+ #[ serde( skip ) ]
398
398
outputs : Vec < PathBuf > ,
399
399
}
400
400
@@ -454,16 +454,65 @@ impl<'de> Deserialize<'de> for DepFingerprint {
454
454
}
455
455
}
456
456
457
+ /// A `LocalFingerprint` represents something that we use to detect direct
458
+ /// changes to a `Fingerprint`.
459
+ ///
460
+ /// This is where we track file information, env vars, etc. This
461
+ /// `LocalFingerprint` struct is hashed and if the hash changes will force a
462
+ /// recompile of any fingerprint it's included into. Note that the "local"
463
+ /// terminology comes from the fact that it only has to do with one crate, and
464
+ /// `Fingerprint` tracks the transitive propagation of fingerprint changes.
465
+ ///
466
+ /// Note that because this is hashed its contents are carefully managed. Like
467
+ /// mentioned in the above module docs, we don't want to hash absolute paths or
468
+ /// mtime information.
469
+ ///
470
+ /// Also note that a `LocalFingerprint` is used in `check_filesystem` to detect
471
+ /// when the filesystem contains stale information (based on mtime currently).
472
+ /// The paths here don't change much between compilations but they're used as
473
+ /// inputs when we probe the filesystem looking at information.
457
474
#[ derive( Debug , Serialize , Deserialize , Hash ) ]
458
475
enum LocalFingerprint {
476
+ /// This is a precalculated fingerprint which has an opaque string we just
477
+ /// hash as usual. This variant is primarily used for git/crates.io
478
+ /// dependencies where the source never changes so we can quickly conclude
479
+ /// that there's some string we can hash and it won't really change much.
480
+ ///
481
+ /// This is also used for build scripts with no `rerun-if-*` statements, but
482
+ /// that's overall a mistake and causes bugs in Cargo. We shouldn't use this
483
+ /// for build scripts.
459
484
Precalculated ( String ) ,
485
+
486
+ /// This is used for crate compilations. The `dep_info` file is a relative
487
+ /// path anchored at `target_root(...)` to the dep-info file that Cargo
488
+ /// generates (which is a custom serialization after parsing rustc's own
489
+ /// `dep-info` output).
490
+ ///
491
+ /// The `dep_info` file, when present, also lists a number of other files
492
+ /// for us to look at. If any of those files are newer than this file then
493
+ /// we need to recompile.
460
494
CheckDepInfo {
461
495
dep_info : PathBuf ,
462
496
} ,
497
+
498
+ /// This represents a nonempty set of `rerun-if-changed` annotations printed
499
+ /// out by a build script. The `output` file is a arelative file anchored at
500
+ /// `target_root(...)` which is the actual output of the build script. That
501
+ /// output has already been parsed and the paths printed out via
502
+ /// `rerun-if-changed` are listed in `paths`. The `paths` field is relative
503
+ /// to `pkg.root()`
504
+ ///
505
+ /// This is considered up-to-date if all of the `paths` are older than
506
+ /// `output`, otherwise we need to recompile.
463
507
RerunIfChanged {
464
508
output : PathBuf ,
465
509
paths : Vec < PathBuf > ,
466
510
} ,
511
+
512
+ /// This represents a single `rerun-if-env-changed` annotation printed by a
513
+ /// build script. The exact env var and value are hashed here. There's no
514
+ /// filesystem dependence here, and if the values are changed the hash will
515
+ /// change forcing a recompile.
467
516
RerunIfEnvChanged {
468
517
var : String ,
469
518
val : Option < String > ,
@@ -778,6 +827,10 @@ impl Fingerprint {
778
827
// If the dependency is newer than our own output then it was
779
828
// recompiled previously. We transitively become stale ourselves in
780
829
// that case, so bail out.
830
+ //
831
+ // Note that this comparison should probably be `>=`, not `>`, but
832
+ // for a discussion of why it's `>` see the discussion about #5918
833
+ // below in `find_stale`.
781
834
if dep_mtime > mtime {
782
835
return Ok ( ( ) ) ;
783
836
}
0 commit comments