Skip to content

Commit 3dc4508

Browse files
committed
Restructure this around changes in rustc PR, also address some review comments
1 parent 5a769f7 commit 3dc4508

File tree

3 files changed

+88
-104
lines changed

3 files changed

+88
-104
lines changed

src/cargo/core/compiler/fingerprint/mod.rs

Lines changed: 74 additions & 94 deletions
Original file line numberDiff line numberDiff line change
@@ -865,18 +865,15 @@ impl LocalFingerprint {
865865
mtime_cache,
866866
checksum_cache,
867867
&dep_info,
868-
info.files.iter().map(|file| {
869-
let checksum = info.checksum.get(file.as_path()).cloned();
870-
(file, checksum)
871-
}),
868+
info.files.iter().map(|(file, checksum)| (file, *checksum)),
872869
*checksum,
873870
))
874871
} else {
875872
Ok(find_stale_file(
876873
mtime_cache,
877874
checksum_cache,
878875
&dep_info,
879-
info.files.into_iter().map(|p| (p, None)),
876+
info.files.into_iter().map(|(p, _checksum)| (p, None)),
880877
*checksum,
881878
))
882879
}
@@ -1935,16 +1932,15 @@ pub fn parse_dep_info(
19351932
};
19361933
let mut ret = RustcDepInfo::default();
19371934
ret.env = info.env;
1938-
ret.files.extend(
1939-
info.files
1940-
.into_iter()
1941-
.map(|(ty, path)| make_absolute_path(ty, pkg_root, target_root, path)),
1942-
);
1943-
for (ty, path, file_len, checksum) in info.checksum {
1944-
let path = make_absolute_path(ty, pkg_root, target_root, path);
1945-
ret.checksum
1946-
.insert(path, (file_len, Checksum::from_str(&checksum)?));
1947-
}
1935+
ret.files
1936+
.extend(info.files.into_iter().map(|(ty, path, checksum_info)| {
1937+
(
1938+
make_absolute_path(ty, pkg_root, target_root, path),
1939+
checksum_info.and_then(|(file_len, checksum)| {
1940+
Checksum::from_str(&checksum).ok().map(|c| (file_len, c))
1941+
}),
1942+
)
1943+
}));
19481944
Ok(Some(ret))
19491945
}
19501946

@@ -2201,21 +2197,14 @@ pub fn translate_dep_info(
22012197
Some((ty, path.to_owned()))
22022198
};
22032199

2204-
for file in depinfo.files {
2205-
let Some(serializable_path) = serialize_path(file) else {
2200+
for (file, checksum_info) in depinfo.files {
2201+
let Some((path_type, path)) = serialize_path(file) else {
22062202
continue;
22072203
};
2208-
on_disk_info.files.push(serializable_path);
2209-
}
2210-
for (file, (file_len, checksum)) in depinfo.checksum {
2211-
let Some(serializable_path) = serialize_path(file) else {
2212-
continue;
2213-
};
2214-
on_disk_info.checksum.push((
2215-
serializable_path.0,
2216-
serializable_path.1,
2217-
file_len,
2218-
checksum.to_string(),
2204+
on_disk_info.files.push((
2205+
path_type,
2206+
path,
2207+
checksum_info.map(|(len, checksum)| (len, checksum.to_string())),
22192208
));
22202209
}
22212210
paths::write(cargo_dep_info, on_disk_info.serialize()?)?;
@@ -2226,7 +2215,7 @@ pub fn translate_dep_info(
22262215
#[derive(Default)]
22272216
pub struct RustcDepInfo {
22282217
/// The list of files that the main target in the dep-info file depends on.
2229-
pub files: Vec<PathBuf>,
2218+
pub files: Vec<(PathBuf, Option<(u64, Checksum)>)>,
22302219
/// The list of environment variables we found that the rustc compilation
22312220
/// depends on.
22322221
///
@@ -2235,10 +2224,6 @@ pub struct RustcDepInfo {
22352224
/// means that the env var wasn't actually set and the compilation depends
22362225
/// on it not being set.
22372226
pub env: Vec<(String, Option<String>)>,
2238-
2239-
/// If provided by rustc, a mapping that ties a file to the checksum and file size
2240-
/// at the time rustc ingested it.
2241-
pub checksum: HashMap<PathBuf, (u64, Checksum)>,
22422227
}
22432228

22442229
/// Same as [`RustcDepInfo`] except avoids absolute paths as much as possible to
@@ -2248,9 +2233,8 @@ pub struct RustcDepInfo {
22482233
/// Cargo will read it for crates on all future compilations.
22492234
#[derive(Default)]
22502235
struct EncodedDepInfo {
2251-
files: Vec<(DepInfoPathType, PathBuf)>,
2236+
files: Vec<(DepInfoPathType, PathBuf, Option<(u64, String)>)>,
22522237
env: Vec<(String, Option<String>)>,
2253-
checksum: Vec<(DepInfoPathType, PathBuf, u64, String)>,
22542238
}
22552239

22562240
impl EncodedDepInfo {
@@ -2264,8 +2248,19 @@ impl EncodedDepInfo {
22642248
1 => DepInfoPathType::TargetRootRelative,
22652249
_ => return None,
22662250
};
2267-
let bytes = read_bytes(bytes)?;
2268-
files.push((ty, paths::bytes2path(bytes).ok()?));
2251+
let path_bytes = read_bytes(bytes)?;
2252+
let path = paths::bytes2path(path_bytes).ok()?;
2253+
let has_checksum = read_bool(bytes)?;
2254+
let checksum_info = has_checksum
2255+
.then(|| {
2256+
let file_len = read_u64(bytes);
2257+
let checksum_string = read_bytes(bytes)
2258+
.map(Vec::from)
2259+
.and_then(|v| String::from_utf8(v).ok());
2260+
file_len.zip(checksum_string)
2261+
})
2262+
.flatten();
2263+
files.push((ty, path, checksum_info));
22692264
}
22702265

22712266
let nenv = read_usize(bytes)?;
@@ -2279,29 +2274,7 @@ impl EncodedDepInfo {
22792274
};
22802275
env.push((key, val));
22812276
}
2282-
let nchecksum = read_usize(bytes)?;
2283-
let mut checksum = Vec::with_capacity(nchecksum);
2284-
for _ in 0..nchecksum {
2285-
let ty = match read_u8(bytes)? {
2286-
0 => DepInfoPathType::PackageRootRelative,
2287-
1 => DepInfoPathType::TargetRootRelative,
2288-
_ => return None,
2289-
};
2290-
let path_bytes = read_bytes(bytes)?;
2291-
let file_len = read_u64(bytes)?;
2292-
let checksum_bytes = read_bytes(bytes)?;
2293-
checksum.push((
2294-
ty,
2295-
paths::bytes2path(path_bytes).ok()?,
2296-
file_len,
2297-
from_utf8(checksum_bytes).ok()?.to_string(),
2298-
));
2299-
}
2300-
return Some(EncodedDepInfo {
2301-
files,
2302-
env,
2303-
checksum,
2304-
});
2277+
return Some(EncodedDepInfo { files, env });
23052278

23062279
fn read_usize(bytes: &mut &[u8]) -> Option<usize> {
23072280
let ret = bytes.get(..4)?;
@@ -2315,6 +2288,12 @@ impl EncodedDepInfo {
23152288
Some(u64::from_le_bytes(ret.try_into().unwrap()))
23162289
}
23172290

2291+
fn read_bool(bytes: &mut &[u8]) -> Option<bool> {
2292+
let ret = bytes.get(0).map(|b| *b != 0)?;
2293+
*bytes = &bytes[1..];
2294+
Some(ret)
2295+
}
2296+
23182297
fn read_u8(bytes: &mut &[u8]) -> Option<u8> {
23192298
let ret = *bytes.get(0)?;
23202299
*bytes = &bytes[1..];
@@ -2333,12 +2312,17 @@ impl EncodedDepInfo {
23332312
let mut ret = Vec::new();
23342313
let dst = &mut ret;
23352314
write_usize(dst, self.files.len());
2336-
for (ty, file) in self.files.iter() {
2315+
for (ty, file, checksum_info) in self.files.iter() {
23372316
match ty {
23382317
DepInfoPathType::PackageRootRelative => dst.push(0),
23392318
DepInfoPathType::TargetRootRelative => dst.push(1),
23402319
}
23412320
write_bytes(dst, paths::path2bytes(file)?);
2321+
write_bool(dst, checksum_info.is_some());
2322+
if let Some((len, checksum)) = checksum_info {
2323+
write_u64(dst, *len);
2324+
write_bytes(dst, checksum);
2325+
}
23422326
}
23432327

23442328
write_usize(dst, self.env.len());
@@ -2352,17 +2336,6 @@ impl EncodedDepInfo {
23522336
}
23532337
}
23542338
}
2355-
2356-
write_usize(dst, self.checksum.len());
2357-
for (ty, file, file_len, checksum) in self.checksum.iter() {
2358-
match ty {
2359-
DepInfoPathType::PackageRootRelative => dst.push(0),
2360-
DepInfoPathType::TargetRootRelative => dst.push(1),
2361-
}
2362-
write_bytes(dst, paths::path2bytes(file)?);
2363-
write_u64(dst, *file_len);
2364-
write_bytes(dst, checksum);
2365-
}
23662339
return Ok(ret);
23672340

23682341
fn write_bytes(dst: &mut Vec<u8>, val: impl AsRef<[u8]>) {
@@ -2378,6 +2351,10 @@ impl EncodedDepInfo {
23782351
fn write_u64(dst: &mut Vec<u8>, val: u64) {
23792352
dst.extend(&u64::to_le_bytes(val));
23802353
}
2354+
2355+
fn write_bool(dst: &mut Vec<u8>, val: bool) {
2356+
dst.push(u8::from(val));
2357+
}
23812358
}
23822359
}
23832360

@@ -2398,39 +2375,42 @@ pub fn parse_rustc_dep_info(rustc_dep_info: &Path) -> CargoResult<RustcDepInfo>
23982375
None => None,
23992376
};
24002377
ret.env.push((unescape_env(env_var)?, env_val));
2401-
} else if let Some(rest) = line.strip_prefix("# checksum:") {
2402-
let mut parts = rest.splitn(3, ' ');
2403-
let Some(checksum) = parts.next().map(Checksum::from_str).transpose()? else {
2404-
continue;
2405-
};
2406-
let Some(Ok(file_len)) = parts
2407-
.next()
2408-
.and_then(|s| s.strip_prefix("file_len:").map(|s| s.parse::<u64>()))
2409-
else {
2410-
continue;
2411-
};
2412-
let Some(path) = parts.next().map(PathBuf::from) else {
2413-
continue;
2414-
};
2415-
2416-
ret.checksum.insert(path, (file_len, checksum));
24172378
} else if let Some(pos) = line.find(": ") {
24182379
if found_deps {
24192380
continue;
24202381
}
2382+
let mut parsing_checksum_index = None;
2383+
let mut last_seen_checksum = None;
24212384
found_deps = true;
24222385
let mut deps = line[pos + 2..].split_whitespace();
24232386

24242387
while let Some(s) = deps.next() {
2425-
let mut file = s.to_string();
2426-
while file.ends_with('\\') {
2427-
file.pop();
2428-
file.push(' ');
2429-
file.push_str(deps.next().ok_or_else(|| {
2388+
let mut word = s.to_string();
2389+
if word == "#" {
2390+
parsing_checksum_index = Some(0);
2391+
continue;
2392+
}
2393+
while word.ends_with('\\') {
2394+
word.pop();
2395+
word.push(' ');
2396+
word.push_str(deps.next().ok_or_else(|| {
24302397
internal("malformed dep-info format, trailing \\".to_string())
24312398
})?);
24322399
}
2433-
ret.files.push(file.into());
2400+
if let Some(parsing_checksum_index) = parsing_checksum_index.as_mut() {
2401+
// By now files list is built, checksum data is provided in the same order as
2402+
// the file list
2403+
if let Some(checksum) = word.strip_prefix("checksum:") {
2404+
last_seen_checksum = Some(Checksum::from_str(checksum)?);
2405+
} else if let Some(file_len) = word.strip_prefix("file_len:") {
2406+
let file_len = file_len.parse::<u64>()?;
2407+
let file_entry = &mut ret.files[*parsing_checksum_index];
2408+
file_entry.1 = last_seen_checksum.take().map(|c| (file_len, c));
2409+
*parsing_checksum_index += 1;
2410+
}
2411+
} else {
2412+
ret.files.push((word.into(), None));
2413+
}
24342414
}
24352415
}
24362416
}

src/cargo/core/compiler/output_depinfo.rs

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -61,7 +61,7 @@ fn add_deps_for_unit(
6161
build_runner.files().host_root(),
6262
&dep_info_loc,
6363
)? {
64-
for path in paths.files {
64+
for (path, _checksum) in paths.files {
6565
deps.insert(path);
6666
}
6767
} else {
@@ -154,7 +154,12 @@ pub fn output_depinfo(build_runner: &mut BuildRunner<'_, '_>, unit: &Unit) -> Ca
154154
// If nothing changed don't recreate the file which could alter
155155
// its mtime
156156
if let Ok(previous) = fingerprint::parse_rustc_dep_info(&output_path) {
157-
if previous.files.iter().eq(deps.iter().map(Path::new)) {
157+
if previous
158+
.files
159+
.iter()
160+
.map(|(path, _checksum)| path)
161+
.eq(deps.iter().map(Path::new))
162+
{
158163
continue;
159164
}
160165
}

tests/testsuite/freshness_checksum.rs

Lines changed: 7 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -159,7 +159,7 @@ fn rebuild_sub_package_then_while_package() {
159159
.masquerade_as_nightly_cargo(&["checksum-freshness"])
160160
.with_stderr(
161161
"\
162-
[LOCKING] 3 packages to latest compatible versions
162+
[LOCKING] 2 packages to latest compatible versions
163163
[CHECKING] b [..]
164164
[CHECKING] a [..]
165165
[CHECKING] foo [..]
@@ -415,7 +415,7 @@ fn changing_bin_paths_common_target_features_caches_targets() {
415415
.with_stdout("ftest off")
416416
.with_stderr(
417417
"\
418-
[LOCKING] 2 packages to latest compatible versions
418+
[LOCKING] 1 package to latest compatible version
419419
[..]Compiling dep_crate v0.0.1 ([..])
420420
[..]Compiling a v0.0.1 ([..])
421421
[FINISHED] `dev` profile [unoptimized + debuginfo] target(s) in [..]
@@ -447,7 +447,7 @@ fn changing_bin_paths_common_target_features_caches_targets() {
447447
.with_stdout("ftest on")
448448
.with_stderr(
449449
"\
450-
[LOCKING] 2 packages to latest compatible versions
450+
[LOCKING] 1 package to latest compatible version
451451
[..]Compiling dep_crate v0.0.1 ([..])
452452
[..]Compiling b v0.0.1 ([..])
453453
[FINISHED] `dev` profile [unoptimized + debuginfo] target(s) in [..]
@@ -824,7 +824,7 @@ fn same_build_dir_cached_packages() {
824824
.cwd("a1")
825825
.with_stderr(&format!(
826826
"\
827-
[LOCKING] 4 packages to latest compatible versions
827+
[LOCKING] 3 packages to latest compatible versions
828828
[CHECKING] d v0.0.1 ({dir}/d)
829829
[CHECKING] c v0.0.1 ({dir}/c)
830830
[CHECKING] b v0.0.1 ({dir}/b)
@@ -839,7 +839,7 @@ fn same_build_dir_cached_packages() {
839839
.cwd("a2")
840840
.with_stderr(
841841
"\
842-
[LOCKING] 4 packages to latest compatible versions
842+
[LOCKING] 3 packages to latest compatible versions
843843
[CHECKING] a2 v0.0.1 ([CWD])
844844
[FINISHED] `dev` profile [unoptimized + debuginfo] target(s) in [..]
845845
",
@@ -1394,7 +1394,7 @@ fn reuse_panic_build_dep_test() {
13941394
.masquerade_as_nightly_cargo(&["checksum-freshness"])
13951395
.with_stderr(
13961396
"\
1397-
[LOCKING] 2 packages to latest compatible versions
1397+
[LOCKING] 1 package to latest compatible version
13981398
[COMPILING] bar [..]
13991399
[RUNNING] `rustc --crate-name bar [..]
14001400
[COMPILING] foo [..]
@@ -1456,7 +1456,7 @@ fn reuse_panic_pm() {
14561456

14571457
.with_stderr_unordered(
14581458
"\
1459-
[LOCKING] 3 packages to latest compatible versions
1459+
[LOCKING] 2 packages to latest compatible versions
14601460
[COMPILING] bar [..]
14611461
[RUNNING] `rustc --crate-name bar --edition=2015 bar/src/lib.rs [..]--crate-type lib --emit=[..]link[..]
14621462
[RUNNING] `rustc --crate-name bar --edition=2015 bar/src/lib.rs [..]--crate-type lib --emit=[..]link -C panic=abort[..]-C debuginfo=2 [..]
@@ -1625,7 +1625,6 @@ fn rebuild_on_mid_build_file_modification() {
16251625
.masquerade_as_nightly_cargo(&["checksum-freshness"])
16261626
.with_stderr(
16271627
"\
1628-
[LOCKING] 2 packages to latest compatible versions
16291628
[COMPILING] proc_macro_dep v0.1.0 ([..]/proc_macro_dep)
16301629
[CHECKING] root v0.1.0 ([..]/root)
16311630
[FINISHED] `dev` profile [unoptimized + debuginfo] target(s) in [..]

0 commit comments

Comments
 (0)