various: translation resources from cg backend

Extend `CodegenBackend` trait with a function returning the translation
resources from the codegen backend, which can be added to the complete
list of resources provided to the emitter.

Signed-off-by: David Wood <david.wood@huawei.com>
This commit is contained in:
David Wood 2022-10-17 14:11:26 +01:00
parent a8e37507f4
commit 26255186e2
23 changed files with 86 additions and 48 deletions

View File

@ -172,6 +172,11 @@ pub struct CraneliftCodegenBackend {
}
impl CodegenBackend for CraneliftCodegenBackend {
fn locale_resource(&self) -> &'static str {
// FIXME(rust-lang/rust#100717) - cranelift codegen backend is not yet translated
""
}
fn init(&self, sess: &Session) {
use rustc_session::config::Lto;
match sess.lto() {

View File

@ -103,6 +103,10 @@ pub struct GccCodegenBackend {
}
impl CodegenBackend for GccCodegenBackend {
fn locale_resource(&self) -> &'static str {
crate::DEFAULT_LOCALE_RESOURCE
}
fn init(&self, sess: &Session) {
if sess.lto() != Lto::No {
sess.emit_warning(LTONotSupported {});

View File

@ -249,6 +249,10 @@ impl LlvmCodegenBackend {
}
impl CodegenBackend for LlvmCodegenBackend {
fn locale_resource(&self) -> &'static str {
crate::DEFAULT_LOCALE_RESOURCE
}
fn init(&self, sess: &Session) {
llvm_util::init(sess); // Make sure llvm is inited
}

View File

@ -57,6 +57,10 @@ impl<'tcx, T> Backend<'tcx> for T where
}
pub trait CodegenBackend {
/// Locale resources for diagnostic messages - a string the content of the Fluent resource.
/// Called before `init` so that all other functions are able to emit translatable diagnostics.
fn locale_resource(&self) -> &'static str;
fn init(&self, _sess: &Session) {}
fn print(&self, _req: PrintRequest, _sess: &Session) {}
fn target_features(&self, _sess: &Session, _allow_unstable: bool) -> Vec<Symbol> {

View File

@ -362,7 +362,7 @@ fn run_compiler(
}
// Make sure name resolution and macro expansion is run.
queries.global_ctxt()?;
queries.global_ctxt()?.enter(|tcx| tcx.resolver_for_lowering(()));
if callbacks.after_expansion(compiler, queries) == Compilation::Stop {
return early_exit();
@ -1204,7 +1204,7 @@ static DEFAULT_HOOK: LazyLock<Box<dyn Fn(&panic::PanicInfo<'_>) + Sync + Send +
/// hook.
pub fn report_ice(info: &panic::PanicInfo<'_>, bug_report_url: &str) {
let fallback_bundle =
rustc_errors::fallback_fluent_bundle(crate::DEFAULT_LOCALE_RESOURCES, false);
rustc_errors::fallback_fluent_bundle(crate::DEFAULT_LOCALE_RESOURCES.to_vec(), false);
let emitter = Box::new(rustc_errors::emitter::EmitterWriter::stderr(
rustc_errors::ColorConfig::Auto,
None,

View File

@ -223,7 +223,7 @@ pub type LazyFallbackBundle = Lrc<Lazy<FluentBundle, impl FnOnce() -> FluentBund
/// Return the default `FluentBundle` with standard "en-US" diagnostic messages.
#[instrument(level = "trace")]
pub fn fallback_fluent_bundle(
resources: &'static [&'static str],
resources: Vec<&'static str>,
with_directionality_markers: bool,
) -> LazyFallbackBundle {
Lrc::new(Lazy::new(move || {

View File

@ -42,11 +42,11 @@ impl<T: Write> Write for Shared<T> {
/// Test the span yields correct positions in JSON.
fn test_positions(code: &str, span: (u32, u32), expected_output: SpanTestData) {
static TEST_LOCALE_RESOURCES: &[&str] = &[crate::DEFAULT_LOCALE_RESOURCE];
rustc_span::create_default_session_globals_then(|| {
let sm = Lrc::new(SourceMap::new(FilePathMapping::empty()));
sm.new_source_file(Path::new("test.rs").to_owned().into(), code.to_owned());
let fallback_bundle = crate::fallback_fluent_bundle(TEST_LOCALE_RESOURCES, false);
let fallback_bundle =
crate::fallback_fluent_bundle(vec![crate::DEFAULT_LOCALE_RESOURCE], false);
let output = Arc::new(Mutex::new(Vec::new()));
let je = JsonEmitter::new(

View File

@ -17,11 +17,11 @@ use rustc_span::{BytePos, FileName, Pos, Span};
use std::path::PathBuf;
static TEST_LOCALE_RESOURCES: &[&str] =
&[crate::DEFAULT_LOCALE_RESOURCE, rustc_parse::DEFAULT_LOCALE_RESOURCE];
fn sess() -> ParseSess {
ParseSess::new(TEST_LOCALE_RESOURCES, FilePathMapping::empty())
ParseSess::new(
vec![crate::DEFAULT_LOCALE_RESOURCE, rustc_parse::DEFAULT_LOCALE_RESOURCE],
FilePathMapping::empty(),
)
}
/// Parses an item.

View File

@ -34,7 +34,10 @@ where
/// Maps a string to tts, using a made-up filename.
pub(crate) fn string_to_stream(source_str: String) -> TokenStream {
let ps = ParseSess::new(TEST_LOCALE_RESOURCES, FilePathMapping::empty());
let ps = ParseSess::new(
vec![crate::DEFAULT_LOCALE_RESOURCE, rustc_parse::DEFAULT_LOCALE_RESOURCE],
FilePathMapping::empty(),
);
source_file_to_stream(
&ps,
ps.source_map().new_source_file(PathBuf::from("bogofile").into(), source_str),
@ -45,7 +48,10 @@ pub(crate) fn string_to_stream(source_str: String) -> TokenStream {
/// Parses a string, returns a crate.
pub(crate) fn string_to_crate(source_str: String) -> ast::Crate {
let ps = ParseSess::new(TEST_LOCALE_RESOURCES, FilePathMapping::empty());
let ps = ParseSess::new(
vec![crate::DEFAULT_LOCALE_RESOURCE, rustc_parse::DEFAULT_LOCALE_RESOURCE],
FilePathMapping::empty(),
);
with_error_checking_parse(source_str, &ps, |p| p.parse_crate_mod())
}
@ -123,14 +129,14 @@ impl<T: Write> Write for Shared<T> {
}
}
static TEST_LOCALE_RESOURCES: &[&str] =
&[crate::DEFAULT_LOCALE_RESOURCE, rustc_parse::DEFAULT_LOCALE_RESOURCE];
fn test_harness(file_text: &str, span_labels: Vec<SpanLabel>, expected_output: &str) {
create_default_session_if_not_set_then(|_| {
let output = Arc::new(Mutex::new(Vec::new()));
let fallback_bundle = rustc_errors::fallback_fluent_bundle(TEST_LOCALE_RESOURCES, false);
let fallback_bundle = rustc_errors::fallback_fluent_bundle(
vec![crate::DEFAULT_LOCALE_RESOURCE, rustc_parse::DEFAULT_LOCALE_RESOURCE],
false,
);
let source_map = Lrc::new(SourceMap::new(FilePathMapping::empty()));
source_map.new_source_file(Path::new("test.rs").to_owned().into(), file_text.to_owned());

View File

@ -50,7 +50,7 @@ fn mk_session(matches: getopts::Matches) -> (Session, CfgSpecs) {
output_file: None,
temps_dir,
};
let sess = build_session(sessopts, io, None, registry, &[], Default::default(), None, None);
let sess = build_session(sessopts, io, None, registry, vec![], Default::default(), None, None);
(sess, cfg)
}

View File

@ -90,6 +90,9 @@ pub fn create_session(
}
};
let mut locale_resources = Vec::from(locale_resources);
locale_resources.push(codegen_backend.locale_resource());
let mut sess = session::build_session(
sopts,
io,

View File

@ -226,10 +226,7 @@ pub struct ParseSess {
impl ParseSess {
/// Used for testing.
pub fn new(
locale_resources: &'static [&'static str],
file_path_mapping: FilePathMapping,
) -> Self {
pub fn new(locale_resources: Vec<&'static str>, file_path_mapping: FilePathMapping) -> Self {
let fallback_bundle = fallback_fluent_bundle(locale_resources, false);
let sm = Lrc::new(SourceMap::new(file_path_mapping));
let handler = Handler::with_tty_emitter(
@ -268,7 +265,7 @@ impl ParseSess {
}
pub fn with_silent_emitter(fatal_note: Option<String>) -> Self {
let fallback_bundle = fallback_fluent_bundle(&[], false);
let fallback_bundle = fallback_fluent_bundle(Vec::new(), false);
let sm = Lrc::new(SourceMap::new(FilePathMapping::empty()));
let fatal_handler =
Handler::with_tty_emitter(ColorConfig::Auto, false, None, None, None, fallback_bundle);

View File

@ -1341,7 +1341,7 @@ pub fn build_session(
io: CompilerIO,
bundle: Option<Lrc<rustc_errors::FluentBundle>>,
registry: rustc_errors::registry::Registry,
fluent_resources: &'static [&'static str],
fluent_resources: Vec<&'static str>,
driver_lint_caps: FxHashMap<lint::LintId, lint::Level>,
file_loader: Option<Box<dyn FileLoader + Send + Sync + 'static>>,
target_override: Option<Target>,
@ -1630,13 +1630,11 @@ pub enum IncrCompSession {
InvalidBecauseOfErrors { session_directory: PathBuf },
}
// FIXME(#100717): early errors aren't translated at the moment, so this is fine, but it will need
// to reference every crate that might emit an early error for translation to work.
static EARLY_ERROR_LOCALE_RESOURCE: &'static [&'static str] =
&[rustc_errors::DEFAULT_LOCALE_RESOURCE];
fn early_error_handler(output: config::ErrorOutputType) -> rustc_errors::Handler {
let fallback_bundle = fallback_fluent_bundle(EARLY_ERROR_LOCALE_RESOURCE, false);
// FIXME(#100717): early errors aren't translated at the moment, so this is fine, but it will
// need to reference every crate that might emit an early error for translation to work.
let fallback_bundle =
fallback_fluent_bundle(vec![rustc_errors::DEFAULT_LOCALE_RESOURCE], false);
let emitter: Box<dyn Emitter + sync::Send> = match output {
config::ErrorOutputType::HumanReadable(kind) => {
let (short, color_config) = kind.unzip();

View File

@ -63,7 +63,8 @@ fn snippet_equal_to_token(tcx: TyCtxt<'_>, matcher: &TokenTree) -> Option<String
let snippet = source_map.span_to_snippet(span).ok()?;
// Create a Parser.
let sess = ParseSess::new(rustc_driver::DEFAULT_LOCALE_RESOURCES, FilePathMapping::empty());
let sess =
ParseSess::new(rustc_driver::DEFAULT_LOCALE_RESOURCES.to_vec(), FilePathMapping::empty());
let file_name = source_map.span_to_filename(span);
let mut parser =
match rustc_parse::maybe_new_parser_from_source_str(&sess, file_name, snippet.clone()) {

View File

@ -115,8 +115,10 @@ pub(crate) fn new_handler(
diagnostic_width: Option<usize>,
unstable_opts: &UnstableOptions,
) -> rustc_errors::Handler {
let fallback_bundle =
rustc_errors::fallback_fluent_bundle(rustc_driver::DEFAULT_LOCALE_RESOURCES, false);
let fallback_bundle = rustc_errors::fallback_fluent_bundle(
rustc_driver::DEFAULT_LOCALE_RESOURCES.to_vec(),
false,
);
let emitter: Box<dyn Emitter + sync::Send> = match error_format {
ErrorOutputType::HumanReadable(kind) => {
let (short, color_config) = kind.unzip();

View File

@ -546,8 +546,10 @@ pub(crate) fn make_test(
// Any errors in parsing should also appear when the doctest is compiled for real, so just
// send all the errors that librustc_ast emits directly into a `Sink` instead of stderr.
let sm = Lrc::new(SourceMap::new(FilePathMapping::empty()));
let fallback_bundle =
rustc_errors::fallback_fluent_bundle(rustc_driver::DEFAULT_LOCALE_RESOURCES, false);
let fallback_bundle = rustc_errors::fallback_fluent_bundle(
rustc_driver::DEFAULT_LOCALE_RESOURCES.to_vec(),
false,
);
supports_color = EmitterWriter::stderr(
ColorConfig::Auto,
None,
@ -742,8 +744,10 @@ fn check_if_attr_is_complete(source: &str, edition: Edition) -> bool {
// Any errors in parsing should also appear when the doctest is compiled for real, so just
// send all the errors that librustc_ast emits directly into a `Sink` instead of stderr.
let sm = Lrc::new(SourceMap::new(FilePathMapping::empty()));
let fallback_bundle =
rustc_errors::fallback_fluent_bundle(rustc_driver::DEFAULT_LOCALE_RESOURCES, false);
let fallback_bundle = rustc_errors::fallback_fluent_bundle(
rustc_driver::DEFAULT_LOCALE_RESOURCES.to_vec(),
false,
);
let emitter = EmitterWriter::new(
Box::new(io::sink()),

View File

@ -33,8 +33,10 @@ fn check_rust_syntax(
code_block: RustCodeBlock,
) {
let buffer = Lrc::new(Lock::new(Buffer::default()));
let fallback_bundle =
rustc_errors::fallback_fluent_bundle(rustc_driver::DEFAULT_LOCALE_RESOURCES, false);
let fallback_bundle = rustc_errors::fallback_fluent_bundle(
rustc_driver::DEFAULT_LOCALE_RESOURCES.to_vec(),
false,
);
let emitter = BufferEmitter { buffer: Lrc::clone(&buffer), fallback_bundle };
let sm = Lrc::new(SourceMap::new(FilePathMapping::empty()));

View File

@ -704,8 +704,10 @@ fn check_code(cx: &LateContext<'_>, text: &str, edition: Edition, span: Span) {
let filename = FileName::anon_source_code(&code);
let sm = Lrc::new(SourceMap::new(FilePathMapping::empty()));
let fallback_bundle =
rustc_errors::fallback_fluent_bundle(rustc_driver::DEFAULT_LOCALE_RESOURCES, false);
let fallback_bundle = rustc_errors::fallback_fluent_bundle(
rustc_driver::DEFAULT_LOCALE_RESOURCES.to_vec(),
false
);
let emitter = EmitterWriter::new(
Box::new(io::sink()),
None,

View File

@ -209,7 +209,10 @@ fn report_clippy_ice(info: &panic::PanicInfo<'_>, bug_report_url: &str) {
// Separate the output with an empty line
eprintln!();
let fallback_bundle = rustc_errors::fallback_fluent_bundle(rustc_driver::DEFAULT_LOCALE_RESOURCES, false);
let fallback_bundle = rustc_errors::fallback_fluent_bundle(
rustc_driver::DEFAULT_LOCALE_RESOURCES.to_vec(),
false
);
let emitter = Box::new(rustc_errors::emitter::EmitterWriter::stderr(
rustc_errors::ColorConfig::Auto,
None,

View File

@ -123,8 +123,10 @@ fn default_handler(
let emitter = if hide_parse_errors {
silent_emitter()
} else {
let fallback_bundle =
rustc_errors::fallback_fluent_bundle(rustc_driver::DEFAULT_LOCALE_RESOURCES, false);
let fallback_bundle = rustc_errors::fallback_fluent_bundle(
rustc_driver::DEFAULT_LOCALE_RESOURCES.to_vec(),
false,
);
Box::new(EmitterWriter::stderr(
color_cfg,
Some(source_map.clone()),

View File

@ -27,6 +27,8 @@ use std::any::Any;
struct TheBackend;
impl CodegenBackend for TheBackend {
fn locale_resource(&self) -> &'static str { "" }
fn codegen_crate<'a, 'tcx>(
&self,
tcx: TyCtxt<'tcx>,

View File

@ -30,10 +30,11 @@ pub fn main() {
assert_eq!(gravy::foo(), 10);
}
static TEST_LOCALE_RESOURCES: &[&str] = &[rustc_parse::DEFAULT_LOCALE_RESOURCE];
fn parse() {
let parse_session = ParseSess::new(TEST_LOCALE_RESOURCES, FilePathMapping::empty());
let parse_session = ParseSess::new(
vec![rustc_parse::DEFAULT_LOCALE_RESOURCE],
FilePathMapping::empty()
);
let path = Path::new(file!());
let path = path.canonicalize().unwrap();

View File

@ -219,10 +219,8 @@ fn main() {
rustc_span::create_default_session_globals_then(|| run());
}
static TEST_LOCALE_RESOURCES: &[&str] = &[rustc_parse::DEFAULT_LOCALE_RESOURCE];
fn run() {
let ps = ParseSess::new(TEST_LOCALE_RESOURCES, FilePathMapping::empty());
let ps = ParseSess::new(vec![rustc_parse::DEFAULT_LOCALE_RESOURCE], FilePathMapping::empty());
iter_exprs(2, &mut |mut e| {
// If the pretty printer is correct, then `parse(print(e))` should be identical to `e`,