]> git.lizzy.rs Git - rust.git/blob - src/bootstrap/builder/tests.rs
Rollup merge of #89422 - GuillaumeGomez:doctest-whitespace-name, r=CraftSpider
[rust.git] / src / bootstrap / builder / tests.rs
1 use super::*;
2 use crate::config::{Config, TargetSelection};
3 use std::thread;
4
5 fn configure(cmd: &str, host: &[&str], target: &[&str]) -> Config {
6     let mut config = Config::parse(&[cmd.to_owned()]);
7     // don't save toolstates
8     config.save_toolstates = None;
9     config.dry_run = true;
10     config.ninja_in_file = false;
11     // try to avoid spurious failures in dist where we create/delete each others file
12     config.out = PathBuf::from(env::var_os("BOOTSTRAP_OUTPUT_DIRECTORY").unwrap());
13     config.initial_rustc = PathBuf::from(env::var_os("RUSTC").unwrap());
14     config.initial_cargo = PathBuf::from(env::var_os("BOOTSTRAP_INITIAL_CARGO").unwrap());
15     let dir = config
16         .out
17         .join("tmp-rustbuild-tests")
18         .join(&thread::current().name().unwrap_or("unknown").replace(":", "-"));
19     t!(fs::create_dir_all(&dir));
20     config.out = dir;
21     config.build = TargetSelection::from_user("A");
22     config.hosts = host.iter().map(|s| TargetSelection::from_user(s)).collect();
23     config.targets = target.iter().map(|s| TargetSelection::from_user(s)).collect();
24     config
25 }
26
27 fn first<A, B>(v: Vec<(A, B)>) -> Vec<A> {
28     v.into_iter().map(|(a, _)| a).collect::<Vec<_>>()
29 }
30
31 mod defaults {
32     use super::{configure, first};
33     use crate::builder::*;
34     use crate::Config;
35     use pretty_assertions::assert_eq;
36
37     #[test]
38     fn build_default() {
39         let build = Build::new(configure("build", &["A"], &["A"]));
40         let mut builder = Builder::new(&build);
41         builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Build), &[]);
42
43         let a = TargetSelection::from_user("A");
44         assert_eq!(
45             first(builder.cache.all::<compile::Std>()),
46             &[
47                 compile::Std { compiler: Compiler { host: a, stage: 0 }, target: a },
48                 compile::Std { compiler: Compiler { host: a, stage: 1 }, target: a },
49             ]
50         );
51         assert!(!builder.cache.all::<compile::Assemble>().is_empty());
52         // Make sure rustdoc is only built once.
53         assert_eq!(
54             first(builder.cache.all::<tool::Rustdoc>()),
55             // Recall that rustdoc stages are off-by-one
56             // - this is the compiler it's _linked_ to, not built with.
57             &[tool::Rustdoc { compiler: Compiler { host: a, stage: 1 } }],
58         );
59         assert_eq!(
60             first(builder.cache.all::<compile::Rustc>()),
61             &[compile::Rustc { compiler: Compiler { host: a, stage: 0 }, target: a },]
62         );
63     }
64
65     #[test]
66     fn build_stage_0() {
67         let config = Config { stage: 0, ..configure("build", &["A"], &["A"]) };
68         let build = Build::new(config);
69         let mut builder = Builder::new(&build);
70         builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Build), &[]);
71
72         let a = TargetSelection::from_user("A");
73         assert_eq!(
74             first(builder.cache.all::<compile::Std>()),
75             &[compile::Std { compiler: Compiler { host: a, stage: 0 }, target: a },]
76         );
77         assert!(!builder.cache.all::<compile::Assemble>().is_empty());
78         assert_eq!(
79             first(builder.cache.all::<tool::Rustdoc>()),
80             // This is the beta rustdoc.
81             // Add an assert here to make sure this is the only rustdoc built.
82             &[tool::Rustdoc { compiler: Compiler { host: a, stage: 0 } }],
83         );
84         assert!(builder.cache.all::<compile::Rustc>().is_empty());
85     }
86
87     #[test]
88     fn build_cross_compile() {
89         let config = Config { stage: 1, ..configure("build", &["A", "B"], &["A", "B"]) };
90         let build = Build::new(config);
91         let mut builder = Builder::new(&build);
92         builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Build), &[]);
93
94         let a = TargetSelection::from_user("A");
95         let b = TargetSelection::from_user("B");
96
97         // Ideally, this build wouldn't actually have `target: a`
98         // rustdoc/rustcc/std here (the user only requested a host=B build, so
99         // there's not really a need for us to build for target A in this case
100         // (since we're producing stage 1 libraries/binaries).  But currently
101         // rustbuild is just a bit buggy here; this should be fixed though.
102         assert_eq!(
103             first(builder.cache.all::<compile::Std>()),
104             &[
105                 compile::Std { compiler: Compiler { host: a, stage: 0 }, target: a },
106                 compile::Std { compiler: Compiler { host: a, stage: 1 }, target: a },
107                 compile::Std { compiler: Compiler { host: a, stage: 0 }, target: b },
108                 compile::Std { compiler: Compiler { host: a, stage: 1 }, target: b },
109             ]
110         );
111         assert_eq!(
112             first(builder.cache.all::<compile::Assemble>()),
113             &[
114                 compile::Assemble { target_compiler: Compiler { host: a, stage: 0 } },
115                 compile::Assemble { target_compiler: Compiler { host: a, stage: 1 } },
116                 compile::Assemble { target_compiler: Compiler { host: b, stage: 1 } },
117             ]
118         );
119         assert_eq!(
120             first(builder.cache.all::<tool::Rustdoc>()),
121             &[
122                 tool::Rustdoc { compiler: Compiler { host: a, stage: 1 } },
123                 tool::Rustdoc { compiler: Compiler { host: b, stage: 1 } },
124             ],
125         );
126         assert_eq!(
127             first(builder.cache.all::<compile::Rustc>()),
128             &[
129                 compile::Rustc { compiler: Compiler { host: a, stage: 0 }, target: a },
130                 compile::Rustc { compiler: Compiler { host: a, stage: 0 }, target: b },
131             ]
132         );
133     }
134
135     #[test]
136     fn doc_default() {
137         let mut config = configure("doc", &["A"], &["A"]);
138         config.compiler_docs = true;
139         config.cmd = Subcommand::Doc { paths: Vec::new(), open: false };
140         let build = Build::new(config);
141         let mut builder = Builder::new(&build);
142         builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Doc), &[]);
143         let a = TargetSelection::from_user("A");
144
145         // error_index_generator uses stage 0 to share rustdoc artifacts with the
146         // rustdoc tool.
147         assert_eq!(
148             first(builder.cache.all::<doc::ErrorIndex>()),
149             &[doc::ErrorIndex { target: a },]
150         );
151         assert_eq!(
152             first(builder.cache.all::<tool::ErrorIndex>()),
153             &[tool::ErrorIndex { compiler: Compiler { host: a, stage: 0 } }]
154         );
155         // docs should be built with the beta compiler, not with the stage0 artifacts.
156         // recall that rustdoc is off-by-one: `stage` is the compiler rustdoc is _linked_ to,
157         // not the one it was built by.
158         assert_eq!(
159             first(builder.cache.all::<tool::Rustdoc>()),
160             &[tool::Rustdoc { compiler: Compiler { host: a, stage: 0 } },]
161         );
162     }
163 }
164
165 mod dist {
166     use super::{first, Config};
167     use crate::builder::*;
168     use pretty_assertions::assert_eq;
169
170     fn configure(host: &[&str], target: &[&str]) -> Config {
171         Config { stage: 2, ..super::configure("dist", host, target) }
172     }
173
174     #[test]
175     fn dist_baseline() {
176         let build = Build::new(configure(&["A"], &["A"]));
177         let mut builder = Builder::new(&build);
178         builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Dist), &[]);
179
180         let a = TargetSelection::from_user("A");
181
182         assert_eq!(first(builder.cache.all::<dist::Docs>()), &[dist::Docs { host: a },]);
183         assert_eq!(first(builder.cache.all::<dist::Mingw>()), &[dist::Mingw { host: a },]);
184         assert_eq!(
185             first(builder.cache.all::<dist::Rustc>()),
186             &[dist::Rustc { compiler: Compiler { host: a, stage: 2 } },]
187         );
188         assert_eq!(
189             first(builder.cache.all::<dist::Std>()),
190             &[dist::Std { compiler: Compiler { host: a, stage: 1 }, target: a },]
191         );
192         assert_eq!(first(builder.cache.all::<dist::Src>()), &[dist::Src]);
193         // Make sure rustdoc is only built once.
194         assert_eq!(
195             first(builder.cache.all::<tool::Rustdoc>()),
196             &[tool::Rustdoc { compiler: Compiler { host: a, stage: 2 } },]
197         );
198     }
199
200     #[test]
201     fn dist_with_targets() {
202         let build = Build::new(configure(&["A"], &["A", "B"]));
203         let mut builder = Builder::new(&build);
204         builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Dist), &[]);
205
206         let a = TargetSelection::from_user("A");
207         let b = TargetSelection::from_user("B");
208
209         assert_eq!(
210             first(builder.cache.all::<dist::Docs>()),
211             &[dist::Docs { host: a }, dist::Docs { host: b },]
212         );
213         assert_eq!(
214             first(builder.cache.all::<dist::Mingw>()),
215             &[dist::Mingw { host: a }, dist::Mingw { host: b },]
216         );
217         assert_eq!(
218             first(builder.cache.all::<dist::Rustc>()),
219             &[dist::Rustc { compiler: Compiler { host: a, stage: 2 } },]
220         );
221         assert_eq!(
222             first(builder.cache.all::<dist::Std>()),
223             &[
224                 dist::Std { compiler: Compiler { host: a, stage: 1 }, target: a },
225                 dist::Std { compiler: Compiler { host: a, stage: 2 }, target: b },
226             ]
227         );
228         assert_eq!(first(builder.cache.all::<dist::Src>()), &[dist::Src]);
229     }
230
231     #[test]
232     fn dist_with_hosts() {
233         let build = Build::new(configure(&["A", "B"], &["A", "B"]));
234         let mut builder = Builder::new(&build);
235         builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Dist), &[]);
236
237         let a = TargetSelection::from_user("A");
238         let b = TargetSelection::from_user("B");
239
240         assert_eq!(
241             first(builder.cache.all::<dist::Docs>()),
242             &[dist::Docs { host: a }, dist::Docs { host: b },]
243         );
244         assert_eq!(
245             first(builder.cache.all::<dist::Mingw>()),
246             &[dist::Mingw { host: a }, dist::Mingw { host: b },]
247         );
248         assert_eq!(
249             first(builder.cache.all::<dist::Rustc>()),
250             &[
251                 dist::Rustc { compiler: Compiler { host: a, stage: 2 } },
252                 dist::Rustc { compiler: Compiler { host: b, stage: 2 } },
253             ]
254         );
255         assert_eq!(
256             first(builder.cache.all::<dist::Std>()),
257             &[
258                 dist::Std { compiler: Compiler { host: a, stage: 1 }, target: a },
259                 dist::Std { compiler: Compiler { host: a, stage: 1 }, target: b },
260             ]
261         );
262         assert_eq!(
263             first(builder.cache.all::<compile::Std>()),
264             &[
265                 compile::Std { compiler: Compiler { host: a, stage: 0 }, target: a },
266                 compile::Std { compiler: Compiler { host: a, stage: 1 }, target: a },
267                 compile::Std { compiler: Compiler { host: a, stage: 2 }, target: a },
268                 compile::Std { compiler: Compiler { host: a, stage: 1 }, target: b },
269                 compile::Std { compiler: Compiler { host: a, stage: 2 }, target: b },
270             ],
271         );
272         assert_eq!(first(builder.cache.all::<dist::Src>()), &[dist::Src]);
273     }
274
275     #[test]
276     fn dist_only_cross_host() {
277         let a = TargetSelection::from_user("A");
278         let b = TargetSelection::from_user("B");
279         let mut build = Build::new(configure(&["A", "B"], &["A", "B"]));
280         build.config.docs = false;
281         build.config.extended = true;
282         build.hosts = vec![b];
283         let mut builder = Builder::new(&build);
284         builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Dist), &[]);
285
286         assert_eq!(
287             first(builder.cache.all::<dist::Rustc>()),
288             &[dist::Rustc { compiler: Compiler { host: b, stage: 2 } },]
289         );
290         assert_eq!(
291             first(builder.cache.all::<compile::Rustc>()),
292             &[
293                 compile::Rustc { compiler: Compiler { host: a, stage: 0 }, target: a },
294                 compile::Rustc { compiler: Compiler { host: a, stage: 1 }, target: b },
295             ]
296         );
297     }
298
299     #[test]
300     fn dist_with_targets_and_hosts() {
301         let build = Build::new(configure(&["A", "B"], &["A", "B", "C"]));
302         let mut builder = Builder::new(&build);
303         builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Dist), &[]);
304
305         let a = TargetSelection::from_user("A");
306         let b = TargetSelection::from_user("B");
307         let c = TargetSelection::from_user("C");
308
309         assert_eq!(
310             first(builder.cache.all::<dist::Docs>()),
311             &[dist::Docs { host: a }, dist::Docs { host: b }, dist::Docs { host: c },]
312         );
313         assert_eq!(
314             first(builder.cache.all::<dist::Mingw>()),
315             &[dist::Mingw { host: a }, dist::Mingw { host: b }, dist::Mingw { host: c },]
316         );
317         assert_eq!(
318             first(builder.cache.all::<dist::Rustc>()),
319             &[
320                 dist::Rustc { compiler: Compiler { host: a, stage: 2 } },
321                 dist::Rustc { compiler: Compiler { host: b, stage: 2 } },
322             ]
323         );
324         assert_eq!(
325             first(builder.cache.all::<dist::Std>()),
326             &[
327                 dist::Std { compiler: Compiler { host: a, stage: 1 }, target: a },
328                 dist::Std { compiler: Compiler { host: a, stage: 1 }, target: b },
329                 dist::Std { compiler: Compiler { host: a, stage: 2 }, target: c },
330             ]
331         );
332         assert_eq!(first(builder.cache.all::<dist::Src>()), &[dist::Src]);
333     }
334
335     #[test]
336     fn dist_with_empty_host() {
337         let config = configure(&[], &["C"]);
338         let build = Build::new(config);
339         let mut builder = Builder::new(&build);
340         builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Dist), &[]);
341
342         let a = TargetSelection::from_user("A");
343         let c = TargetSelection::from_user("C");
344
345         assert_eq!(first(builder.cache.all::<dist::Docs>()), &[dist::Docs { host: c },]);
346         assert_eq!(first(builder.cache.all::<dist::Mingw>()), &[dist::Mingw { host: c },]);
347         assert_eq!(
348             first(builder.cache.all::<dist::Std>()),
349             &[dist::Std { compiler: Compiler { host: a, stage: 2 }, target: c },]
350         );
351     }
352
353     #[test]
354     fn dist_with_same_targets_and_hosts() {
355         let build = Build::new(configure(&["A", "B"], &["A", "B"]));
356         let mut builder = Builder::new(&build);
357         builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Dist), &[]);
358
359         let a = TargetSelection::from_user("A");
360         let b = TargetSelection::from_user("B");
361
362         assert_eq!(
363             first(builder.cache.all::<dist::Docs>()),
364             &[dist::Docs { host: a }, dist::Docs { host: b },]
365         );
366         assert_eq!(
367             first(builder.cache.all::<dist::Mingw>()),
368             &[dist::Mingw { host: a }, dist::Mingw { host: b },]
369         );
370         assert_eq!(
371             first(builder.cache.all::<dist::Rustc>()),
372             &[
373                 dist::Rustc { compiler: Compiler { host: a, stage: 2 } },
374                 dist::Rustc { compiler: Compiler { host: b, stage: 2 } },
375             ]
376         );
377         assert_eq!(
378             first(builder.cache.all::<dist::Std>()),
379             &[
380                 dist::Std { compiler: Compiler { host: a, stage: 1 }, target: a },
381                 dist::Std { compiler: Compiler { host: a, stage: 1 }, target: b },
382             ]
383         );
384         assert_eq!(first(builder.cache.all::<dist::Src>()), &[dist::Src]);
385         assert_eq!(
386             first(builder.cache.all::<compile::Std>()),
387             &[
388                 compile::Std { compiler: Compiler { host: a, stage: 0 }, target: a },
389                 compile::Std { compiler: Compiler { host: a, stage: 1 }, target: a },
390                 compile::Std { compiler: Compiler { host: a, stage: 2 }, target: a },
391                 compile::Std { compiler: Compiler { host: a, stage: 1 }, target: b },
392                 compile::Std { compiler: Compiler { host: a, stage: 2 }, target: b },
393             ]
394         );
395         assert_eq!(
396             first(builder.cache.all::<compile::Assemble>()),
397             &[
398                 compile::Assemble { target_compiler: Compiler { host: a, stage: 0 } },
399                 compile::Assemble { target_compiler: Compiler { host: a, stage: 1 } },
400                 compile::Assemble { target_compiler: Compiler { host: a, stage: 2 } },
401                 compile::Assemble { target_compiler: Compiler { host: b, stage: 2 } },
402             ]
403         );
404     }
405
406     #[test]
407     fn build_all() {
408         let build = Build::new(configure(&["A", "B"], &["A", "B", "C"]));
409         let mut builder = Builder::new(&build);
410         builder.run_step_descriptions(
411             &Builder::get_step_descriptions(Kind::Build),
412             &["compiler/rustc".into(), "library/std".into()],
413         );
414
415         let a = TargetSelection::from_user("A");
416         let b = TargetSelection::from_user("B");
417         let c = TargetSelection::from_user("C");
418
419         assert_eq!(
420             first(builder.cache.all::<compile::Std>()),
421             &[
422                 compile::Std { compiler: Compiler { host: a, stage: 0 }, target: a },
423                 compile::Std { compiler: Compiler { host: a, stage: 1 }, target: a },
424                 compile::Std { compiler: Compiler { host: a, stage: 2 }, target: a },
425                 compile::Std { compiler: Compiler { host: a, stage: 1 }, target: b },
426                 compile::Std { compiler: Compiler { host: a, stage: 2 }, target: b },
427                 compile::Std { compiler: Compiler { host: a, stage: 2 }, target: c },
428             ]
429         );
430         assert!(!builder.cache.all::<compile::Assemble>().is_empty());
431         assert_eq!(
432             first(builder.cache.all::<compile::Rustc>()),
433             &[
434                 compile::Rustc { compiler: Compiler { host: a, stage: 0 }, target: a },
435                 compile::Rustc { compiler: Compiler { host: a, stage: 1 }, target: a },
436                 compile::Rustc { compiler: Compiler { host: a, stage: 2 }, target: a },
437                 compile::Rustc { compiler: Compiler { host: a, stage: 1 }, target: b },
438                 compile::Rustc { compiler: Compiler { host: a, stage: 2 }, target: b },
439             ]
440         );
441     }
442
443     #[test]
444     fn build_with_empty_host() {
445         let config = configure(&[], &["C"]);
446         let build = Build::new(config);
447         let mut builder = Builder::new(&build);
448         builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Build), &[]);
449
450         let a = TargetSelection::from_user("A");
451         let c = TargetSelection::from_user("C");
452
453         assert_eq!(
454             first(builder.cache.all::<compile::Std>()),
455             &[
456                 compile::Std { compiler: Compiler { host: a, stage: 0 }, target: a },
457                 compile::Std { compiler: Compiler { host: a, stage: 1 }, target: a },
458                 compile::Std { compiler: Compiler { host: a, stage: 2 }, target: c },
459             ]
460         );
461         assert_eq!(
462             first(builder.cache.all::<compile::Assemble>()),
463             &[
464                 compile::Assemble { target_compiler: Compiler { host: a, stage: 0 } },
465                 compile::Assemble { target_compiler: Compiler { host: a, stage: 1 } },
466                 compile::Assemble { target_compiler: Compiler { host: a, stage: 2 } },
467             ]
468         );
469         assert_eq!(
470             first(builder.cache.all::<compile::Rustc>()),
471             &[
472                 compile::Rustc { compiler: Compiler { host: a, stage: 0 }, target: a },
473                 compile::Rustc { compiler: Compiler { host: a, stage: 1 }, target: a },
474             ]
475         );
476     }
477
478     #[test]
479     fn test_with_no_doc_stage0() {
480         let mut config = configure(&["A"], &["A"]);
481         config.stage = 0;
482         config.cmd = Subcommand::Test {
483             paths: vec!["library/std".into()],
484             test_args: vec![],
485             rustc_args: vec![],
486             fail_fast: true,
487             doc_tests: DocTests::No,
488             bless: false,
489             force_rerun: false,
490             compare_mode: None,
491             rustfix_coverage: false,
492             pass: None,
493             run: None,
494         };
495
496         let build = Build::new(config);
497         let mut builder = Builder::new(&build);
498
499         let host = TargetSelection::from_user("A");
500
501         builder.run_step_descriptions(
502             &[StepDescription::from::<test::Crate>()],
503             &["library/std".into()],
504         );
505
506         // Ensure we don't build any compiler artifacts.
507         assert!(!builder.cache.contains::<compile::Rustc>());
508         assert_eq!(
509             first(builder.cache.all::<test::Crate>()),
510             &[test::Crate {
511                 compiler: Compiler { host, stage: 0 },
512                 target: host,
513                 mode: Mode::Std,
514                 test_kind: test::TestKind::Test,
515                 krate: INTERNER.intern_str("std"),
516             },]
517         );
518     }
519
520     #[test]
521     fn test_exclude() {
522         let mut config = configure(&["A"], &["A"]);
523         config.exclude = vec!["src/tools/tidy".into()];
524         config.cmd = Subcommand::Test {
525             paths: Vec::new(),
526             test_args: Vec::new(),
527             rustc_args: Vec::new(),
528             fail_fast: true,
529             doc_tests: DocTests::No,
530             bless: false,
531             force_rerun: false,
532             compare_mode: None,
533             rustfix_coverage: false,
534             pass: None,
535             run: None,
536         };
537
538         let build = Build::new(config);
539         let builder = Builder::new(&build);
540         builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Test), &[]);
541
542         // Ensure we have really excluded tidy
543         assert!(!builder.cache.contains::<test::Tidy>());
544
545         // Ensure other tests are not affected.
546         assert!(builder.cache.contains::<test::RustdocUi>());
547     }
548
549     #[test]
550     fn doc_ci() {
551         let mut config = configure(&["A"], &["A"]);
552         config.compiler_docs = true;
553         config.cmd = Subcommand::Doc { paths: Vec::new(), open: false };
554         let build = Build::new(config);
555         let mut builder = Builder::new(&build);
556         builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Doc), &[]);
557         let a = TargetSelection::from_user("A");
558
559         // error_index_generator uses stage 1 to share rustdoc artifacts with the
560         // rustdoc tool.
561         assert_eq!(
562             first(builder.cache.all::<doc::ErrorIndex>()),
563             &[doc::ErrorIndex { target: a },]
564         );
565         assert_eq!(
566             first(builder.cache.all::<tool::ErrorIndex>()),
567             &[tool::ErrorIndex { compiler: Compiler { host: a, stage: 1 } }]
568         );
569         // This is actually stage 1, but Rustdoc::run swaps out the compiler with
570         // stage minus 1 if --stage is not 0. Very confusing!
571         assert_eq!(
572             first(builder.cache.all::<tool::Rustdoc>()),
573             &[tool::Rustdoc { compiler: Compiler { host: a, stage: 2 } },]
574         );
575     }
576
577     #[test]
578     fn test_docs() {
579         // Behavior of `x.py test` doing various documentation tests.
580         let mut config = configure(&["A"], &["A"]);
581         config.cmd = Subcommand::Test {
582             paths: vec![],
583             test_args: vec![],
584             rustc_args: vec![],
585             fail_fast: true,
586             doc_tests: DocTests::Yes,
587             bless: false,
588             force_rerun: false,
589             compare_mode: None,
590             rustfix_coverage: false,
591             pass: None,
592             run: None,
593         };
594         // Make sure rustfmt binary not being found isn't an error.
595         config.channel = "beta".to_string();
596         let build = Build::new(config);
597         let mut builder = Builder::new(&build);
598
599         builder.run_step_descriptions(&Builder::get_step_descriptions(Kind::Test), &[]);
600         let a = TargetSelection::from_user("A");
601
602         // error_index_generator uses stage 1 to share rustdoc artifacts with the
603         // rustdoc tool.
604         assert_eq!(
605             first(builder.cache.all::<doc::ErrorIndex>()),
606             &[doc::ErrorIndex { target: a },]
607         );
608         assert_eq!(
609             first(builder.cache.all::<tool::ErrorIndex>()),
610             &[tool::ErrorIndex { compiler: Compiler { host: a, stage: 1 } }]
611         );
612         // Unfortunately rustdoc is built twice. Once from stage1 for compiletest
613         // (and other things), and once from stage0 for std crates. Ideally it
614         // would only be built once. If someone wants to fix this, it might be
615         // worth investigating if it would be possible to test std from stage1.
616         // Note that the stages here are +1 than what they actually are because
617         // Rustdoc::run swaps out the compiler with stage minus 1 if --stage is
618         // not 0.
619         //
620         // The stage 0 copy is the one downloaded for bootstrapping. It is
621         // (currently) needed to run "cargo test" on the linkchecker, and
622         // should be relatively "free".
623         assert_eq!(
624             first(builder.cache.all::<tool::Rustdoc>()),
625             &[
626                 tool::Rustdoc { compiler: Compiler { host: a, stage: 0 } },
627                 tool::Rustdoc { compiler: Compiler { host: a, stage: 1 } },
628                 tool::Rustdoc { compiler: Compiler { host: a, stage: 2 } },
629             ]
630         );
631     }
632 }