Skip to content

Commit

Permalink
Rollup merge of rust-lang#107096 - clubby789:fluent-bad-messageref, r…
Browse files Browse the repository at this point in the history
…=compiler-errors

Detect references to non-existant messages in Fluent resources

Should help with cases like rust-lang#107091, where `{variable}` (a message reference) is accidentally typed, rather than `{$variable}` (a variable reference)

`@rustbot` label +A-translation
  • Loading branch information
JohnTitor authored Jan 27, 2023
2 parents a4e6bb0 + 89b1f39 commit c28bf74
Show file tree
Hide file tree
Showing 6 changed files with 54 additions and 6 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ codegen_gcc_invalid_monomorphization_unsupported_element =
invalid monomorphization of `{$name}` intrinsic: unsupported {$name} from `{$in_ty}` with element `{$elem_ty}` to `{$ret_ty}`
codegen_gcc_invalid_monomorphization_invalid_bitmask =
invalid monomorphization of `{$name}` intrinsic: invalid bitmask `{ty}`, expected `u{$expected_int_bits}` or `[u8; {$expected_bytes}]`
invalid monomorphization of `{$name}` intrinsic: invalid bitmask `{$ty}`, expected `u{$expected_int_bits}` or `[u8; {$expected_bytes}]`
codegen_gcc_invalid_monomorphization_simd_shuffle =
invalid monomorphization of `{$name}` intrinsic: simd_shuffle index must be an array of `u32`, got `{$ty}`
Expand Down
4 changes: 2 additions & 2 deletions compiler/rustc_error_messages/locales/en-US/codegen_ssa.ftl
Original file line number Diff line number Diff line change
Expand Up @@ -179,9 +179,9 @@ codegen_ssa_extract_bundled_libs_write_file = failed to write file '{$rlib}': {$
codegen_ssa_unsupported_arch = unsupported arch `{$arch}` for os `{$os}`
codegen_ssa_apple_sdk_error_sdk_path = failed to get {$sdk_name} SDK path: {error}
codegen_ssa_apple_sdk_error_sdk_path = failed to get {$sdk_name} SDK path: {$error}
codegen_ssa_read_file = failed to read file: {message}
codegen_ssa_read_file = failed to read file: {$message}
codegen_ssa_unsupported_link_self_contained = option `-C link-self-contained` is not supported on this target
Expand Down
34 changes: 32 additions & 2 deletions compiler/rustc_macros/src/diagnostics/fluent.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,10 @@ use annotate_snippets::{
};
use fluent_bundle::{FluentBundle, FluentError, FluentResource};
use fluent_syntax::{
ast::{Attribute, Entry, Identifier, Message},
ast::{
Attribute, Entry, Expression, Identifier, InlineExpression, Message, Pattern,
PatternElement,
},
parser::ParserError,
};
use proc_macro::{Diagnostic, Level, Span};
Expand Down Expand Up @@ -185,9 +188,12 @@ pub(crate) fn fluent_messages(input: proc_macro::TokenStream) -> proc_macro::Tok
};

let mut constants = TokenStream::new();
let mut messagerefs = HashMap::new();
for entry in resource.entries() {
let span = res.krate.span();
if let Entry::Message(Message { id: Identifier { name }, attributes, .. }) = entry {
if let Entry::Message(Message { id: Identifier { name }, attributes, value, .. }) =
entry
{
let _ = previous_defns.entry(name.to_string()).or_insert(path_span);

if name.contains('-') {
Expand All @@ -200,6 +206,18 @@ pub(crate) fn fluent_messages(input: proc_macro::TokenStream) -> proc_macro::Tok
.emit();
}

if let Some(Pattern { elements }) = value {
for elt in elements {
if let PatternElement::Placeable {
expression:
Expression::Inline(InlineExpression::MessageReference { id, .. }),
} = elt
{
messagerefs.insert(id.name, *name);
}
}
}

// Require that the message name starts with the crate name
// `hir_typeck_foo_bar` (in `hir_typeck.ftl`)
// `const_eval_baz` (in `const_eval.ftl`)
Expand Down Expand Up @@ -258,6 +276,18 @@ pub(crate) fn fluent_messages(input: proc_macro::TokenStream) -> proc_macro::Tok
}
}

for (&mref, &name) in messagerefs.iter() {
if !previous_defns.contains_key(mref) {
Diagnostic::spanned(
path_span,
Level::Error,
format!("referenced message `{mref}` does not exist (in message `{name}`)"),
)
.help(&format!("you may have meant to use a variable reference (`{{${mref}}}`)"))
.emit();
}
}

if let Err(errs) = bundle.add_resource(resource) {
for e in errs {
match e {
Expand Down
1 change: 1 addition & 0 deletions tests/ui-fulldeps/fluent-messages/missing-message-ref.ftl
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
missing_message_ref = {message}
9 changes: 9 additions & 0 deletions tests/ui-fulldeps/fluent-messages/test.rs
Original file line number Diff line number Diff line change
Expand Up @@ -96,3 +96,12 @@ mod missing_crate_name {

use self::fluent_generated::{DEFAULT_LOCALE_RESOURCES, test_crate_foo, with_hyphens};
}

mod missing_message_ref {
use super::fluent_messages;

fluent_messages! {
missing => "./missing-message-ref.ftl"
//~^ ERROR referenced message `message` does not exist
}
}
10 changes: 9 additions & 1 deletion tests/ui-fulldeps/fluent-messages/test.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -93,6 +93,14 @@ LL | test_crate => "./missing-crate-name.ftl",
|
= help: replace any '-'s with '_'s

error: aborting due to 10 previous errors
error: referenced message `message` does not exist (in message `missing_message_ref`)
--> $DIR/test.rs:104:20
|
LL | missing => "./missing-message-ref.ftl"
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
= help: you may have meant to use a variable reference (`{$message}`)

error: aborting due to 11 previous errors

For more information about this error, try `rustc --explain E0428`.

0 comments on commit c28bf74

Please sign in to comment.