@@ -6,8 +6,8 @@ use crate::common::{Assembly, Incremental, JsDocTest, MirOpt, RunMake, RustdocJs
66use crate :: common:: { Codegen , CodegenUnits , DebugInfo , Debugger , Rustdoc } ;
77use crate :: common:: { CompareMode , FailMode , PassMode } ;
88use crate :: common:: { Config , TestPaths } ;
9- use crate :: common:: { Pretty , RunCoverage , RunPassValgrind } ;
10- use crate :: common:: { UI_COVERAGE , UI_RUN_STDERR , UI_RUN_STDOUT } ;
9+ use crate :: common:: { CoverageMap , Pretty , RunCoverage , RunPassValgrind } ;
10+ use crate :: common:: { UI_COVERAGE , UI_COVERAGE_MAP , UI_RUN_STDERR , UI_RUN_STDOUT } ;
1111use crate :: compute_diff:: { write_diff, write_filtered_diff} ;
1212use crate :: errors:: { self , Error , ErrorKind } ;
1313use crate :: header:: TestProps ;
@@ -254,6 +254,7 @@ impl<'test> TestCx<'test> {
254254 MirOpt => self . run_mir_opt_test ( ) ,
255255 Assembly => self . run_assembly_test ( ) ,
256256 JsDocTest => self . run_js_doc_test ( ) ,
257+ CoverageMap => self . run_coverage_map_test ( ) ,
257258 RunCoverage => self . run_coverage_test ( ) ,
258259 }
259260 }
@@ -467,6 +468,46 @@ impl<'test> TestCx<'test> {
467468 }
468469 }
469470
471+ fn run_coverage_map_test ( & self ) {
472+ let Some ( coverage_dump_path) = & self . config . coverage_dump_path else {
473+ self . fatal ( "missing --coverage-dump" ) ;
474+ } ;
475+
476+ let proc_res = self . compile_test_and_save_ir ( ) ;
477+ if !proc_res. status . success ( ) {
478+ self . fatal_proc_rec ( "compilation failed!" , & proc_res) ;
479+ }
480+ drop ( proc_res) ;
481+
482+ let llvm_ir_path = self . output_base_name ( ) . with_extension ( "ll" ) ;
483+
484+ let mut dump_command = Command :: new ( coverage_dump_path) ;
485+ dump_command. arg ( llvm_ir_path) ;
486+ let proc_res = self . run_command_to_procres ( & mut dump_command) ;
487+ if !proc_res. status . success ( ) {
488+ self . fatal_proc_rec ( "coverage-dump failed!" , & proc_res) ;
489+ }
490+
491+ let kind = UI_COVERAGE_MAP ;
492+
493+ let expected_coverage_dump = self . load_expected_output ( kind) ;
494+ let actual_coverage_dump = self . normalize_output ( & proc_res. stdout , & [ ] ) ;
495+
496+ let coverage_dump_errors = self . compare_output (
497+ kind,
498+ & actual_coverage_dump,
499+ & expected_coverage_dump,
500+ self . props . compare_output_lines_by_subset ,
501+ ) ;
502+
503+ if coverage_dump_errors > 0 {
504+ self . fatal_proc_rec (
505+ & format ! ( "{coverage_dump_errors} errors occurred comparing coverage output." ) ,
506+ & proc_res,
507+ ) ;
508+ }
509+ }
510+
470511 fn run_coverage_test ( & self ) {
471512 let should_run = self . run_if_enabled ( ) ;
472513 let proc_res = self . compile_test ( should_run, Emit :: None ) ;
@@ -650,6 +691,10 @@ impl<'test> TestCx<'test> {
650691 let mut cmd = Command :: new ( tool_path) ;
651692 configure_cmd_fn ( & mut cmd) ;
652693
694+ self . run_command_to_procres ( & mut cmd)
695+ }
696+
697+ fn run_command_to_procres ( & self , cmd : & mut Command ) -> ProcRes {
653698 let output = cmd. output ( ) . unwrap_or_else ( |_| panic ! ( "failed to exec `{cmd:?}`" ) ) ;
654699
655700 let proc_res = ProcRes {
@@ -2321,9 +2366,11 @@ impl<'test> TestCx<'test> {
23212366 }
23222367 }
23232368 DebugInfo => { /* debuginfo tests must be unoptimized */ }
2324- RunCoverage => {
2325- // Coverage reports are affected by optimization level, and
2326- // the current snapshots assume no optimization by default.
2369+ CoverageMap | RunCoverage => {
2370+ // Coverage mappings and coverage reports are affected by
2371+ // optimization level, so they ignore the optimize-tests
2372+ // setting and set an optimization level in their mode's
2373+ // compile flags (below) or in per-test `compile-flags`.
23272374 }
23282375 _ => {
23292376 rustc. arg ( "-O" ) ;
@@ -2392,8 +2439,22 @@ impl<'test> TestCx<'test> {
23922439
23932440 rustc. arg ( dir_opt) ;
23942441 }
2442+ CoverageMap => {
2443+ rustc. arg ( "-Cinstrument-coverage" ) ;
2444+ // These tests only compile to MIR, so they don't need the
2445+ // profiler runtime to be present.
2446+ rustc. arg ( "-Zno-profiler-runtime" ) ;
2447+ // Coverage mappings are sensitive to MIR optimizations, and
2448+ // the current snapshots assume `opt-level=2` unless overridden
2449+ // by `compile-flags`.
2450+ rustc. arg ( "-Copt-level=2" ) ;
2451+ }
23952452 RunCoverage => {
23962453 rustc. arg ( "-Cinstrument-coverage" ) ;
2454+ // Coverage reports are sometimes sensitive to optimizations,
2455+ // and the current snapshots assume no optimization unless
2456+ // overridden by `compile-flags`.
2457+ rustc. arg ( "-Copt-level=0" ) ;
23972458 }
23982459 RunPassValgrind | Pretty | DebugInfo | Codegen | Rustdoc | RustdocJson | RunMake
23992460 | CodegenUnits | JsDocTest | Assembly => {
0 commit comments