@@ -7,6 +7,7 @@ use std::str::FromStr;
77
88use rustc_data_structures:: fx:: FxHashMap ;
99use rustc_driver:: print_flag_list;
10+ use rustc_errors:: ErrorGuaranteed ;
1011use rustc_session:: config:: {
1112 self , parse_crate_types_from_list, parse_externs, parse_target_triple, CrateType ,
1213} ;
@@ -21,6 +22,14 @@ use rustc_span::edition::Edition;
2122use rustc_target:: spec:: TargetTriple ;
2223
2324use crate :: core:: new_handler;
25+ use crate :: errors:: {
26+ CannotUseOutDirAndOutputFlags , ErrorLoadingThemeFile , ExtendCssArgNotFile , FlagDeprecated ,
27+ FlagRemoved , FlagRemovedSuggestion , GenerateLinkToDefinitionFlagNotWithHtmlOutputFormat ,
28+ HtmlOutputNotSupportedWithShowCoverageFlag , IndexPageArgNotFile , InvalidExternHtmlRootUrl ,
29+ MissingFileOperand , NoRunFlagWithoutTestFlag , ThemeArgNotCssFile , ThemeArgNotFile ,
30+ ThemeFileMissingDefaultThemeCssRules , TooManyFileOperands , UnknownCrateType ,
31+ UnknownInputFormat , UnrecognizedEmissionType ,
32+ } ;
2433use crate :: externalfiles:: ExternalHtml ;
2534use crate :: html;
2635use crate :: html:: markdown:: IdMap ;
@@ -396,7 +405,7 @@ impl Options {
396405 match kind. parse ( ) {
397406 Ok ( kind) => emit. push ( kind) ,
398407 Err ( ( ) ) => {
399- diag. err ( & format ! ( "unrecognized emission type: {}" , kind) ) ;
408+ diag. emit_err ( UnrecognizedEmissionType { kind } ) ;
400409 return Err ( 1 ) ;
401410 }
402411 }
@@ -452,10 +461,10 @@ impl Options {
452461 let input = PathBuf :: from ( if describe_lints {
453462 "" // dummy, this won't be used
454463 } else if matches. free . is_empty ( ) {
455- diag. struct_err ( "missing file operand" ) . emit ( ) ;
464+ diag. emit_err ( MissingFileOperand ) ;
456465 return Err ( 1 ) ;
457466 } else if matches. free . len ( ) > 1 {
458- diag. struct_err ( "too many file operands" ) . emit ( ) ;
467+ diag. emit_err ( TooManyFileOperands ) ;
459468 return Err ( 1 ) ;
460469 } else {
461470 & matches. free [ 0 ]
@@ -467,13 +476,7 @@ impl Options {
467476 . map ( |s| SearchPath :: from_cli_opt ( s, error_format) )
468477 . collect ( ) ;
469478 let externs = parse_externs ( matches, & unstable_opts, error_format) ;
470- let extern_html_root_urls = match parse_extern_html_roots ( matches) {
471- Ok ( ex) => ex,
472- Err ( err) => {
473- diag. struct_err ( err) . emit ( ) ;
474- return Err ( 1 ) ;
475- }
476- } ;
479+ let extern_html_root_urls = parse_extern_html_roots ( matches, & diag) . map_err ( |_| 1 ) ?;
477480
478481 let default_settings: Vec < Vec < ( String , String ) > > = vec ! [
479482 matches
@@ -529,15 +532,15 @@ impl Options {
529532 let no_run = matches. opt_present ( "no-run" ) ;
530533
531534 if !should_test && no_run {
532- diag. err ( "the `--test` flag must be passed to enable `--no-run`" ) ;
535+ diag. emit_err ( NoRunFlagWithoutTestFlag ) ;
533536 return Err ( 1 ) ;
534537 }
535538
536539 let out_dir = matches. opt_str ( "out-dir" ) . map ( |s| PathBuf :: from ( & s) ) ;
537540 let output = matches. opt_str ( "output" ) . map ( |s| PathBuf :: from ( & s) ) ;
538541 let output = match ( out_dir, output) {
539542 ( Some ( _) , Some ( _) ) => {
540- diag. struct_err ( "cannot use both 'out-dir' and 'output' at once" ) . emit ( ) ;
543+ diag. emit_err ( CannotUseOutDirAndOutputFlags ) ;
541544 return Err ( 1 ) ;
542545 }
543546 ( Some ( out_dir) , None ) => out_dir,
@@ -552,7 +555,7 @@ impl Options {
552555
553556 if let Some ( ref p) = extension_css {
554557 if !p. is_file ( ) {
555- diag. struct_err ( "option --extend-css argument must be a file" ) . emit ( ) ;
558+ diag. emit_err ( ExtendCssArgNotFile ) ;
556559 return Err ( 1 ) ;
557560 }
558561 }
@@ -573,32 +576,19 @@ impl Options {
573576 matches. opt_strs ( "theme" ) . iter ( ) . map ( |s| ( PathBuf :: from ( & s) , s. to_owned ( ) ) )
574577 {
575578 if !theme_file. is_file ( ) {
576- diag. struct_err ( & format ! ( "invalid argument: \" {}\" " , theme_s) )
577- . help ( "arguments to --theme must be files" )
578- . emit ( ) ;
579+ diag. emit_err ( ThemeArgNotFile { theme_arg : & theme_s } ) ;
579580 return Err ( 1 ) ;
580581 }
581582 if theme_file. extension ( ) != Some ( OsStr :: new ( "css" ) ) {
582- diag. struct_err ( & format ! ( "invalid argument: \" {}\" " , theme_s) )
583- . help ( "arguments to --theme must have a .css extension" )
584- . emit ( ) ;
583+ diag. emit_err ( ThemeArgNotCssFile { theme_arg : & theme_s } ) ;
585584 return Err ( 1 ) ;
586585 }
587586 let ( success, ret) = theme:: test_theme_against ( & theme_file, & paths, & diag) ;
588587 if !success {
589- diag. struct_err ( & format ! ( "error loading theme file: \" {} \" " , theme_s) ) . emit ( ) ;
588+ diag. emit_err ( ErrorLoadingThemeFile { theme_arg : & theme_s } ) ;
590589 return Err ( 1 ) ;
591590 } else if !ret. is_empty ( ) {
592- diag. struct_warn ( & format ! (
593- "theme file \" {}\" is missing CSS rules from the default theme" ,
594- theme_s
595- ) )
596- . warn ( "the theme may appear incorrect when loaded" )
597- . help ( & format ! (
598- "to see what rules are missing, call `rustdoc --check-theme \" {}\" `" ,
599- theme_s
600- ) )
601- . emit ( ) ;
591+ diag. emit_warning ( ThemeFileMissingDefaultThemeCssRules { theme_arg : & theme_s } ) ;
602592 }
603593 themes. push ( StylePath { path : theme_file } ) ;
604594 }
@@ -625,15 +615,15 @@ impl Options {
625615 match matches. opt_str ( "r" ) . as_deref ( ) {
626616 Some ( "rust" ) | None => { }
627617 Some ( s) => {
628- diag. struct_err ( & format ! ( "unknown input format: {}" , s ) ) . emit ( ) ;
618+ diag. emit_err ( UnknownInputFormat { input_format_arg : s } ) ;
629619 return Err ( 1 ) ;
630620 }
631621 }
632622
633623 let index_page = matches. opt_str ( "index-page" ) . map ( |s| PathBuf :: from ( & s) ) ;
634624 if let Some ( ref index_page) = index_page {
635625 if !index_page. is_file ( ) {
636- diag. struct_err ( "option `--index-page` argument must be a file" ) . emit ( ) ;
626+ diag. emit_err ( IndexPageArgNotFile ) ;
637627 return Err ( 1 ) ;
638628 }
639629 }
@@ -644,8 +634,8 @@ impl Options {
644634
645635 let crate_types = match parse_crate_types_from_list ( matches. opt_strs ( "crate-type" ) ) {
646636 Ok ( types) => types,
647- Err ( e ) => {
648- diag. struct_err ( & format ! ( "unknown crate type: {}" , e ) ) . emit ( ) ;
637+ Err ( error ) => {
638+ diag. emit_err ( UnknownCrateType { error } ) ;
649639 return Err ( 1 ) ;
650640 }
651641 } ;
@@ -654,10 +644,7 @@ impl Options {
654644 Some ( s) => match OutputFormat :: try_from ( s. as_str ( ) ) {
655645 Ok ( out_fmt) => {
656646 if !out_fmt. is_json ( ) && show_coverage {
657- diag. struct_err (
658- "html output format isn't supported for the --show-coverage option" ,
659- )
660- . emit ( ) ;
647+ diag. emit_err ( HtmlOutputNotSupportedWithShowCoverageFlag ) ;
661648 return Err ( 1 ) ;
662649 }
663650 out_fmt
@@ -707,10 +694,7 @@ impl Options {
707694 matches. opt_present ( "extern-html-root-takes-precedence" ) ;
708695
709696 if generate_link_to_definition && ( show_coverage || output_format != OutputFormat :: Html ) {
710- diag. struct_err (
711- "--generate-link-to-definition option can only be used with HTML output format" ,
712- )
713- . emit ( ) ;
697+ diag. emit_err ( GenerateLinkToDefinitionFlagNotWithHtmlOutputFormat ) ;
714698 return Err ( 1 ) ;
715699 }
716700
@@ -804,32 +788,23 @@ fn check_deprecated_options(matches: &getopts::Matches, diag: &rustc_errors::Han
804788
805789 for & flag in deprecated_flags. iter ( ) {
806790 if matches. opt_present ( flag) {
807- diag. struct_warn ( & format ! ( "the `{}` flag is deprecated" , flag) )
808- . note (
809- "see issue #44136 <https://github.com/rust-lang/rust/issues/44136> \
810- for more information",
811- )
812- . emit ( ) ;
791+ diag. emit_warning ( FlagDeprecated { flag } ) ;
813792 }
814793 }
815794
816795 let removed_flags = [ "plugins" , "plugin-path" , "no-defaults" , "passes" , "input-format" ] ;
817796
818797 for & flag in removed_flags. iter ( ) {
819798 if matches. opt_present ( flag) {
820- let mut err = diag. struct_warn ( & format ! ( "the `{}` flag no longer functions" , flag) ) ;
821- err. note (
822- "see issue #44136 <https://github.com/rust-lang/rust/issues/44136> \
823- for more information",
824- ) ;
825-
826- if flag == "no-defaults" || flag == "passes" {
827- err. help ( "you may want to use --document-private-items" ) ;
799+ let suggestion = if flag == "no-defaults" || flag == "passes" {
800+ Some ( FlagRemovedSuggestion :: DocumentPrivateItems )
828801 } else if flag == "plugins" || flag == "plugin-path" {
829- err. warn ( "see CVE-2018-1000622" ) ;
830- }
802+ Some ( FlagRemovedSuggestion :: SeeRustdocPluginsCve )
803+ } else {
804+ None
805+ } ;
831806
832- err . emit ( ) ;
807+ diag . emit_warning ( FlagRemoved { flag , suggestion } ) ;
833808 }
834809 }
835810}
@@ -839,11 +814,12 @@ fn check_deprecated_options(matches: &getopts::Matches, diag: &rustc_errors::Han
839814/// describing the issue.
840815fn parse_extern_html_roots (
841816 matches : & getopts:: Matches ,
842- ) -> Result < BTreeMap < String , String > , & ' static str > {
817+ diag : & rustc_errors:: Handler ,
818+ ) -> Result < BTreeMap < String , String > , ErrorGuaranteed > {
843819 let mut externs = BTreeMap :: new ( ) ;
844820 for arg in & matches. opt_strs ( "extern-html-root-url" ) {
845821 let ( name, url) =
846- arg. split_once ( '=' ) . ok_or ( "--extern-html-root-url must be of the form name=url" ) ?;
822+ arg. split_once ( '=' ) . ok_or_else ( || diag . emit_err ( InvalidExternHtmlRootUrl ) ) ?;
847823 externs. insert ( name. to_string ( ) , url. to_string ( ) ) ;
848824 }
849825 Ok ( externs)
0 commit comments