Skip to content

Commit d75fd91

Browse files
committed
Migrate ast_lowering::ast to SessionDiagnostic
1 parent 1382d30 commit d75fd91

File tree

3 files changed

+239
-100
lines changed

3 files changed

+239
-100
lines changed

compiler/rustc_ast_lowering/src/asm.rs

Lines changed: 62 additions & 99 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,17 @@
11
use crate::{ImplTraitContext, ImplTraitPosition, ParamMode, ResolverAstLoweringExt};
22

3+
use super::errors::{
4+
AbiSpecifiedMultipleTimes, AttSyntaxOnlyX86, ClobberAbiNotSupported,
5+
InlineAsmUnsupportedTarget, InvalidAbiClobberAbi, InvalidAsmTemplateModifierConst,
6+
InvalidAsmTemplateModifierRegClass, InvalidAsmTemplateModifierRegClassSub,
7+
InvalidAsmTemplateModifierSym, InvalidRegister, InvalidRegisterClass, RegisterClassOnlyClobber,
8+
RegisterConflict,
9+
};
310
use super::LoweringContext;
411

512
use rustc_ast::ptr::P;
613
use rustc_ast::*;
714
use rustc_data_structures::fx::{FxHashMap, FxHashSet};
8-
use rustc_errors::struct_span_err;
915
use rustc_hir as hir;
1016
use rustc_hir::def::{DefKind, Res};
1117
use rustc_hir::definitions::DefPathData;
@@ -26,13 +32,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
2632
let asm_arch =
2733
if self.tcx.sess.opts.actually_rustdoc { None } else { self.tcx.sess.asm_arch };
2834
if asm_arch.is_none() && !self.tcx.sess.opts.actually_rustdoc {
29-
struct_span_err!(
30-
self.tcx.sess,
31-
sp,
32-
E0472,
33-
"inline assembly is unsupported on this target"
34-
)
35-
.emit();
35+
self.tcx.sess.emit_err(InlineAsmUnsupportedTarget { span: sp });
3636
}
3737
if let Some(asm_arch) = asm_arch {
3838
// Inline assembly is currently only stable for these architectures.
@@ -59,10 +59,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
5959
&& !matches!(asm_arch, Some(asm::InlineAsmArch::X86 | asm::InlineAsmArch::X86_64))
6060
&& !self.tcx.sess.opts.actually_rustdoc
6161
{
62-
self.tcx
63-
.sess
64-
.struct_span_err(sp, "the `att_syntax` option is only supported on x86")
65-
.emit();
62+
self.tcx.sess.emit_err(AttSyntaxOnlyX86 { span: sp });
6663
}
6764
if asm.options.contains(InlineAsmOptions::MAY_UNWIND) && !self.tcx.features().asm_unwind {
6865
feature_err(
@@ -82,51 +79,37 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
8279
// If the abi was already in the list, emit an error
8380
match clobber_abis.get(&abi) {
8481
Some((prev_name, prev_sp)) => {
85-
let mut err = self.tcx.sess.struct_span_err(
86-
*abi_span,
87-
&format!("`{}` ABI specified multiple times", prev_name),
88-
);
89-
err.span_label(*prev_sp, "previously specified here");
90-
9182
// Multiple different abi names may actually be the same ABI
9283
// If the specified ABIs are not the same name, alert the user that they resolve to the same ABI
9384
let source_map = self.tcx.sess.source_map();
94-
if source_map.span_to_snippet(*prev_sp)
95-
!= source_map.span_to_snippet(*abi_span)
96-
{
97-
err.note("these ABIs are equivalent on the current target");
98-
}
85+
let equivalent = (source_map.span_to_snippet(*prev_sp)
86+
!= source_map.span_to_snippet(*abi_span))
87+
.then_some(());
9988

100-
err.emit();
89+
self.tcx.sess.emit_err(AbiSpecifiedMultipleTimes {
90+
abi_span: *abi_span,
91+
prev_name: *prev_name,
92+
prev_span: *prev_sp,
93+
equivalent,
94+
});
10195
}
10296
None => {
103-
clobber_abis.insert(abi, (abi_name, *abi_span));
97+
clobber_abis.insert(abi, (*abi_name, *abi_span));
10498
}
10599
}
106100
}
107101
Err(&[]) => {
108-
self.tcx
109-
.sess
110-
.struct_span_err(
111-
*abi_span,
112-
"`clobber_abi` is not supported on this target",
113-
)
114-
.emit();
102+
self.tcx.sess.emit_err(ClobberAbiNotSupported { abi_span: *abi_span });
115103
}
116104
Err(supported_abis) => {
117-
let mut err = self
118-
.tcx
119-
.sess
120-
.struct_span_err(*abi_span, "invalid ABI for `clobber_abi`");
121105
let mut abis = format!("`{}`", supported_abis[0]);
122106
for m in &supported_abis[1..] {
123107
let _ = write!(abis, ", `{}`", m);
124108
}
125-
err.note(&format!(
126-
"the following ABIs are supported on this target: {}",
127-
abis
128-
));
129-
err.emit();
109+
self.tcx.sess.emit_err(InvalidAbiClobberAbi {
110+
abi_span: *abi_span,
111+
supported_abis: abis,
112+
});
130113
}
131114
}
132115
}
@@ -144,8 +127,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
144127
InlineAsmRegOrRegClass::Reg(s) => {
145128
asm::InlineAsmRegOrRegClass::Reg(if let Some(asm_arch) = asm_arch {
146129
asm::InlineAsmReg::parse(asm_arch, s).unwrap_or_else(|e| {
147-
let msg = format!("invalid register `{}`: {}", s, e);
148-
sess.struct_span_err(*op_sp, &msg).emit();
130+
sess.emit_err(InvalidRegister { op_span: *op_sp, s, e });
149131
asm::InlineAsmReg::Err
150132
})
151133
} else {
@@ -155,8 +137,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
155137
InlineAsmRegOrRegClass::RegClass(s) => {
156138
asm::InlineAsmRegOrRegClass::RegClass(if let Some(asm_arch) = asm_arch {
157139
asm::InlineAsmRegClass::parse(asm_arch, s).unwrap_or_else(|e| {
158-
let msg = format!("invalid register class `{}`: {}", s, e);
159-
sess.struct_span_err(*op_sp, &msg).emit();
140+
sess.emit_err(InvalidRegisterClass { op_span: *op_sp, s, e });
160141
asm::InlineAsmRegClass::Err
161142
})
162143
} else {
@@ -282,50 +263,39 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
282263
}
283264
let valid_modifiers = class.valid_modifiers(asm_arch.unwrap());
284265
if !valid_modifiers.contains(&modifier) {
285-
let mut err = sess.struct_span_err(
286-
placeholder_span,
287-
"invalid asm template modifier for this register class",
288-
);
289-
err.span_label(placeholder_span, "template modifier");
290-
err.span_label(op_sp, "argument");
291-
if !valid_modifiers.is_empty() {
266+
let sub = if !valid_modifiers.is_empty() {
292267
let mut mods = format!("`{}`", valid_modifiers[0]);
293268
for m in &valid_modifiers[1..] {
294269
let _ = write!(mods, ", `{}`", m);
295270
}
296-
err.note(&format!(
297-
"the `{}` register class supports \
298-
the following template modifiers: {}",
299-
class.name(),
300-
mods
301-
));
271+
InvalidAsmTemplateModifierRegClassSub::SupportModifier {
272+
class_name: class.name(),
273+
modifiers: mods,
274+
}
302275
} else {
303-
err.note(&format!(
304-
"the `{}` register class does not support template modifiers",
305-
class.name()
306-
));
307-
}
308-
err.emit();
276+
InvalidAsmTemplateModifierRegClassSub::DoesNotSupportModifier {
277+
class_name: class.name(),
278+
}
279+
};
280+
sess.emit_err(InvalidAsmTemplateModifierRegClass {
281+
placeholder_span,
282+
op_span: op_sp,
283+
sub,
284+
});
309285
}
310286
}
311287
hir::InlineAsmOperand::Const { .. } => {
312-
let mut err = sess.struct_span_err(
288+
sess.emit_err(InvalidAsmTemplateModifierConst {
313289
placeholder_span,
314-
"asm template modifiers are not allowed for `const` arguments",
315-
);
316-
err.span_label(placeholder_span, "template modifier");
317-
err.span_label(op_sp, "argument");
318-
err.emit();
290+
op_span: op_sp,
291+
});
319292
}
320293
hir::InlineAsmOperand::SymFn { .. }
321294
| hir::InlineAsmOperand::SymStatic { .. } => {
322-
let mut err = sess.struct_span_err(
295+
sess.emit_err(InvalidAsmTemplateModifierSym {
323296
placeholder_span,
324-
"asm template modifiers are not allowed for `sym` arguments",
325-
);
326-
err.span_label(placeholder_span, "template modifier");
327-
err.span_label(op_sp, "argument");
328-
err.emit();
297+
op_span: op_sp,
298+
});
329299
}
330300
}
331301
}
@@ -346,12 +316,10 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
346316
// require that the operand name an explicit register, not a
347317
// register class.
348318
if reg_class.is_clobber_only(asm_arch.unwrap()) && !op.is_clobber() {
349-
let msg = format!(
350-
"register class `{}` can only be used as a clobber, \
351-
not as an input or output",
352-
reg_class.name()
353-
);
354-
sess.struct_span_err(op_sp, &msg).emit();
319+
sess.emit_err(RegisterClassOnlyClobber {
320+
op_span: op_sp,
321+
reg_class_name: reg_class.name(),
322+
});
355323
continue;
356324
}
357325

@@ -391,16 +359,7 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
391359
unreachable!();
392360
};
393361

394-
let msg = format!(
395-
"register `{}` conflicts with register `{}`",
396-
reg.name(),
397-
reg2.name()
398-
);
399-
let mut err = sess.struct_span_err(op_sp, &msg);
400-
err.span_label(op_sp, &format!("register `{}`", reg.name()));
401-
err.span_label(op_sp2, &format!("register `{}`", reg2.name()));
402-
403-
match (op, op2) {
362+
let in_out = match (op, op2) {
404363
(
405364
hir::InlineAsmOperand::In { .. },
406365
hir::InlineAsmOperand::Out { late, .. },
@@ -411,14 +370,18 @@ impl<'a, 'hir> LoweringContext<'a, 'hir> {
411370
) => {
412371
assert!(!*late);
413372
let out_op_sp = if input { op_sp2 } else { op_sp };
414-
let msg = "use `lateout` instead of \
415-
`out` to avoid conflict";
416-
err.span_help(out_op_sp, msg);
417-
}
418-
_ => {}
419-
}
373+
Some(out_op_sp)
374+
},
375+
_ => None,
376+
};
420377

421-
err.emit();
378+
sess.emit_err(RegisterConflict {
379+
op_span1: op_sp,
380+
op_span2: op_sp2,
381+
reg1_name: reg.name(),
382+
reg2_name: reg2.name(),
383+
in_out
384+
});
422385
}
423386
Entry::Vacant(v) => {
424387
if r == reg {

compiler/rustc_ast_lowering/src/errors.rs

Lines changed: 123 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
use rustc_errors::{fluent, AddSubdiagnostic, Applicability, Diagnostic};
2-
use rustc_macros::SessionDiagnostic;
2+
use rustc_macros::{SessionDiagnostic, SessionSubdiagnostic};
33
use rustc_span::{Span, Symbol};
44

55
#[derive(SessionDiagnostic, Clone, Copy)]
@@ -148,3 +148,125 @@ pub struct AsyncGeneratorsNotSupported {
148148
#[primary_span]
149149
pub span: Span,
150150
}
151+
152+
#[derive(SessionDiagnostic, Clone, Copy)]
153+
#[error(ast_lowering::inline_asm_unsupported_target, code = "E0472")]
154+
pub struct InlineAsmUnsupportedTarget {
155+
#[primary_span]
156+
pub span: Span,
157+
}
158+
159+
#[derive(SessionDiagnostic, Clone, Copy)]
160+
#[error(ast_lowering::att_syntax_only_x86)]
161+
pub struct AttSyntaxOnlyX86 {
162+
#[primary_span]
163+
pub span: Span,
164+
}
165+
166+
#[derive(SessionDiagnostic, Clone, Copy)]
167+
#[error(ast_lowering::abi_specified_multiple_times)]
168+
pub struct AbiSpecifiedMultipleTimes {
169+
#[primary_span]
170+
pub abi_span: Span,
171+
pub prev_name: Symbol,
172+
#[label]
173+
pub prev_span: Span,
174+
#[note]
175+
pub equivalent: Option<()>,
176+
}
177+
178+
#[derive(SessionDiagnostic, Clone, Copy)]
179+
#[error(ast_lowering::clobber_abi_not_supported)]
180+
pub struct ClobberAbiNotSupported {
181+
#[primary_span]
182+
pub abi_span: Span,
183+
}
184+
185+
#[derive(SessionDiagnostic)]
186+
#[note]
187+
#[error(ast_lowering::invalid_abi_clobber_abi)]
188+
pub struct InvalidAbiClobberAbi {
189+
#[primary_span]
190+
pub abi_span: Span,
191+
pub supported_abis: String,
192+
}
193+
194+
#[derive(SessionDiagnostic, Clone, Copy)]
195+
#[error(ast_lowering::invalid_register)]
196+
pub struct InvalidRegister<'a> {
197+
#[primary_span]
198+
pub op_span: Span,
199+
pub s: Symbol,
200+
pub e: &'a str,
201+
}
202+
203+
#[derive(SessionDiagnostic, Clone, Copy)]
204+
#[error(ast_lowering::invalid_register_class)]
205+
pub struct InvalidRegisterClass<'a> {
206+
#[primary_span]
207+
pub op_span: Span,
208+
pub s: Symbol,
209+
pub e: &'a str,
210+
}
211+
212+
#[derive(SessionDiagnostic)]
213+
#[error(ast_lowering::invalid_asm_template_modifier_reg_class)]
214+
pub struct InvalidAsmTemplateModifierRegClass {
215+
#[primary_span]
216+
#[label(ast_lowering::template_modifier)]
217+
pub placeholder_span: Span,
218+
#[label(ast_lowering::argument)]
219+
pub op_span: Span,
220+
#[subdiagnostic]
221+
pub sub: InvalidAsmTemplateModifierRegClassSub,
222+
}
223+
224+
#[derive(SessionSubdiagnostic)]
225+
pub enum InvalidAsmTemplateModifierRegClassSub {
226+
#[note(ast_lowering::support_modifiers)]
227+
SupportModifier { class_name: Symbol, modifiers: String },
228+
#[note(ast_lowering::does_not_support_modifiers)]
229+
DoesNotSupportModifier { class_name: Symbol },
230+
}
231+
232+
#[derive(SessionDiagnostic, Clone, Copy)]
233+
#[error(ast_lowering::invalid_asm_template_modifier_const)]
234+
pub struct InvalidAsmTemplateModifierConst {
235+
#[primary_span]
236+
#[label(ast_lowering::template_modifier)]
237+
pub placeholder_span: Span,
238+
#[label(ast_lowering::argument)]
239+
pub op_span: Span,
240+
}
241+
242+
#[derive(SessionDiagnostic, Clone, Copy)]
243+
#[error(ast_lowering::invalid_asm_template_modifier_sym)]
244+
pub struct InvalidAsmTemplateModifierSym {
245+
#[primary_span]
246+
#[label(ast_lowering::template_modifier)]
247+
pub placeholder_span: Span,
248+
#[label(ast_lowering::argument)]
249+
pub op_span: Span,
250+
}
251+
252+
#[derive(SessionDiagnostic, Clone, Copy)]
253+
#[error(ast_lowering::register_class_only_clobber)]
254+
pub struct RegisterClassOnlyClobber {
255+
#[primary_span]
256+
pub op_span: Span,
257+
pub reg_class_name: Symbol,
258+
}
259+
260+
#[derive(SessionDiagnostic, Clone, Copy)]
261+
#[error(ast_lowering::register_conflict)]
262+
pub struct RegisterConflict<'a> {
263+
#[primary_span]
264+
#[label(ast_lowering::register1)]
265+
pub op_span1: Span,
266+
#[label(ast_lowering::register2)]
267+
pub op_span2: Span,
268+
pub reg1_name: &'a str,
269+
pub reg2_name: &'a str,
270+
#[help]
271+
pub in_out: Option<Span>,
272+
}

0 commit comments

Comments
 (0)