Skip to content

Commit 3b4ff16

Browse files
committed
Clean up rustc_session::output::{find,validate}_crate_name
1 parent d8810e3 commit 3b4ff16

File tree

4 files changed

+61
-58
lines changed

4 files changed

+61
-58
lines changed

compiler/rustc_session/messages.ftl

+3-3
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ session_cannot_mix_and_match_sanitizers = `-Zsanitizer={$first}` is incompatible
88
session_cli_feature_diagnostic_help =
99
add `-Zcrate-attr="feature({$feature})"` to the command-line options to enable
1010
11-
session_crate_name_does_not_match = `--crate-name` and `#[crate_name]` are required to match, but `{$s}` != `{$name}`
11+
session_crate_name_does_not_match = `--crate-name` and `#[crate_name]` are required to match, but `{$crate_name}` != `{$attr_crate_name}`
1212
1313
session_crate_name_empty = crate name must not be empty
1414
@@ -52,8 +52,8 @@ session_instrumentation_not_supported = {$us} instrumentation is not supported f
5252
session_int_literal_too_large = integer literal is too large
5353
.note = value exceeds limit of `{$limit}`
5454
55-
session_invalid_character_in_create_name = invalid character `{$character}` in crate name: `{$crate_name}`
56-
session_invalid_character_in_create_name_help = you can either pass `--crate-name` on the command line or add `#![crate_name="…"]` to set the crate name
55+
session_invalid_character_in_crate_name = invalid character {$character} in crate name: `{$crate_name}`
56+
.help = you can either pass `--crate-name` on the command line or add `#![crate_name = "…"]` to set the crate name
5757
5858
session_invalid_float_literal_suffix = invalid suffix `{$suffix}` for float literal
5959
.label = invalid suffix `{$suffix}`

compiler/rustc_session/src/errors.rs

+5-11
Original file line numberDiff line numberDiff line change
@@ -217,8 +217,8 @@ pub(crate) struct FileWriteFail<'a> {
217217
pub(crate) struct CrateNameDoesNotMatch {
218218
#[primary_span]
219219
pub(crate) span: Span,
220-
pub(crate) s: Symbol,
221-
pub(crate) name: Symbol,
220+
pub(crate) crate_name: Symbol,
221+
pub(crate) attr_crate_name: Symbol,
222222
}
223223

224224
#[derive(Diagnostic)]
@@ -235,20 +235,14 @@ pub(crate) struct CrateNameEmpty {
235235
}
236236

237237
#[derive(Diagnostic)]
238-
#[diag(session_invalid_character_in_create_name)]
238+
#[diag(session_invalid_character_in_crate_name)]
239239
pub(crate) struct InvalidCharacterInCrateName {
240240
#[primary_span]
241241
pub(crate) span: Option<Span>,
242242
pub(crate) character: char,
243243
pub(crate) crate_name: Symbol,
244-
#[subdiagnostic]
245-
pub(crate) crate_name_help: Option<InvalidCrateNameHelp>,
246-
}
247-
248-
#[derive(Subdiagnostic)]
249-
pub(crate) enum InvalidCrateNameHelp {
250-
#[help(session_invalid_character_in_create_name_help)]
251-
AddCrateName,
244+
#[help]
245+
pub(crate) help: Option<()>,
252246
}
253247

254248
#[derive(Subdiagnostic)]

compiler/rustc_session/src/output.rs

+51-42
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ use crate::Session;
99
use crate::config::{self, CrateType, Input, OutFileName, OutputFilenames, OutputType};
1010
use crate::errors::{
1111
self, CrateNameDoesNotMatch, CrateNameEmpty, CrateNameInvalid, FileIsNotWriteable,
12-
InvalidCharacterInCrateName, InvalidCrateNameHelp,
12+
InvalidCharacterInCrateName,
1313
};
1414

1515
pub fn out_filename(
@@ -49,10 +49,13 @@ fn is_writeable(p: &Path) -> bool {
4949
}
5050
}
5151

52+
/// Find and [validate] the crate name.
53+
///
54+
/// [validate]: validate_crate_name
5255
pub fn find_crate_name(sess: &Session, attrs: &[ast::Attribute]) -> Symbol {
53-
let validate = |s: Symbol, span: Option<Span>| {
54-
validate_crate_name(sess, s, span);
55-
s
56+
let validate = |name, span| {
57+
validate_crate_name(sess, name, span);
58+
name
5659
};
5760

5861
// Look in attributes 100% of the time to make sure the attribute is marked
@@ -62,56 +65,62 @@ pub fn find_crate_name(sess: &Session, attrs: &[ast::Attribute]) -> Symbol {
6265
let attr_crate_name =
6366
attr::find_by_name(attrs, sym::crate_name).and_then(|at| at.value_str().map(|s| (at, s)));
6467

65-
if let Some(ref s) = sess.opts.crate_name {
66-
let s = Symbol::intern(s);
67-
if let Some((attr, name)) = attr_crate_name {
68-
if name != s {
69-
sess.dcx().emit_err(CrateNameDoesNotMatch { span: attr.span, s, name });
70-
}
68+
if let Some(crate_name) = &sess.opts.crate_name {
69+
let crate_name = Symbol::intern(crate_name);
70+
if let Some((attr, attr_crate_name)) = attr_crate_name
71+
&& attr_crate_name != crate_name
72+
{
73+
sess.dcx().emit_err(CrateNameDoesNotMatch {
74+
span: attr.span,
75+
crate_name,
76+
attr_crate_name,
77+
});
7178
}
72-
return validate(s, None);
79+
return validate(crate_name, None);
7380
}
7481

75-
if let Some((attr, s)) = attr_crate_name {
76-
return validate(s, Some(attr.span));
82+
if let Some((attr, crate_name)) = attr_crate_name {
83+
return validate(crate_name, Some(attr.span));
7784
}
78-
if let Input::File(ref path) = sess.io.input {
79-
if let Some(s) = path.file_stem().and_then(|s| s.to_str()) {
80-
if s.starts_with('-') {
81-
sess.dcx().emit_err(CrateNameInvalid { s });
82-
} else {
83-
return validate(Symbol::intern(&s.replace('-', "_")), None);
84-
}
85+
86+
if let Input::File(ref path) = sess.io.input
87+
&& let Some(s) = path.file_stem().and_then(|s| s.to_str())
88+
{
89+
if s.starts_with('-') {
90+
sess.dcx().emit_err(CrateNameInvalid { s });
91+
} else {
92+
return validate(Symbol::intern(&s.replace('-', "_")), None);
8593
}
8694
}
8795

8896
sym::rust_out
8997
}
9098

91-
pub fn validate_crate_name(sess: &Session, s: Symbol, sp: Option<Span>) {
99+
/// Validate the given crate name.
100+
///
101+
/// Note that this validation is more permissive than identifier parsing. It considers
102+
/// non-empty sequences of alphanumeric and underscore characters to be valid crate names.
103+
/// Most notably, it accepts names starting with a numeric character like `0`!
104+
///
105+
/// Furthermore, this shouldn't be taken as the canonical crate name validator.
106+
/// Other places may use a more restrictive grammar (e.g., identifier or ASCII identifier).
107+
pub fn validate_crate_name(sess: &Session, crate_name: Symbol, span: Option<Span>) {
92108
let mut guar = None;
93-
{
94-
if s.is_empty() {
95-
guar = Some(sess.dcx().emit_err(CrateNameEmpty { span: sp }));
96-
}
97-
for c in s.as_str().chars() {
98-
if c.is_alphanumeric() {
99-
continue;
100-
}
101-
if c == '_' {
102-
continue;
103-
}
104-
guar = Some(sess.dcx().emit_err(InvalidCharacterInCrateName {
105-
span: sp,
106-
character: c,
107-
crate_name: s,
108-
crate_name_help: if sp.is_none() {
109-
Some(InvalidCrateNameHelp::AddCrateName)
110-
} else {
111-
None
112-
},
113-
}));
109+
110+
if crate_name.is_empty() {
111+
guar = Some(sess.dcx().emit_err(CrateNameEmpty { span }));
112+
}
113+
114+
for c in crate_name.as_str().chars() {
115+
if c.is_alphanumeric() || c == '_' {
116+
continue;
114117
}
118+
guar = Some(sess.dcx().emit_err(InvalidCharacterInCrateName {
119+
span,
120+
character: c,
121+
crate_name,
122+
help: span.is_none().then_some(()),
123+
}));
115124
}
116125

117126
if let Some(guar) = guar {
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
1-
error: invalid character `'$'` in crate name: `need_crate_arg_ignore_tidy$x`
1+
error: invalid character '$' in crate name: `need_crate_arg_ignore_tidy$x`
22
|
3-
= help: you can either pass `--crate-name` on the command line or add `#![crate_name="…"]` to set the crate name
3+
= help: you can either pass `--crate-name` on the command line or add `#![crate_name = "…"]` to set the crate name
44

55
error: aborting due to 1 previous error
66

0 commit comments

Comments
 (0)