diff options
| -rw-r--r-- | compiler/rustc_ast_passes/messages.ftl | 4 | ||||
| -rw-r--r-- | compiler/rustc_ast_passes/src/ast_validation.rs | 9 | ||||
| -rw-r--r-- | compiler/rustc_ast_passes/src/errors.rs | 12 | ||||
| -rw-r--r-- | tests/ui/c-variadic/not-async.rs | 7 | ||||
| -rw-r--r-- | tests/ui/c-variadic/not-async.stderr | 19 | ||||
| -rw-r--r-- | tests/ui/inference/note-and-explain-ReVar-124973.rs | 3 | ||||
| -rw-r--r-- | tests/ui/inference/note-and-explain-ReVar-124973.stderr | 8 |
7 files changed, 60 insertions, 2 deletions
diff --git a/compiler/rustc_ast_passes/messages.ftl b/compiler/rustc_ast_passes/messages.ftl index e5f1fcdc4b4..68ac2a05a48 100644 --- a/compiler/rustc_ast_passes/messages.ftl +++ b/compiler/rustc_ast_passes/messages.ftl @@ -84,6 +84,10 @@ ast_passes_const_without_body = ast_passes_constraint_on_negative_bound = associated type constraints not allowed on negative bounds +ast_passes_coroutine_and_c_variadic = functions cannot be both `{$coroutine_kind}` and C-variadic + .const = `{$coroutine_kind}` because of this + .variadic = C-variadic because of this + ast_passes_equality_in_where = equality constraints are not yet supported in `where` clauses .label = not supported .suggestion = if `{$ident}` is an associated type you're trying to set, use the associated type binding syntax diff --git a/compiler/rustc_ast_passes/src/ast_validation.rs b/compiler/rustc_ast_passes/src/ast_validation.rs index 538918a890d..672c1e94418 100644 --- a/compiler/rustc_ast_passes/src/ast_validation.rs +++ b/compiler/rustc_ast_passes/src/ast_validation.rs @@ -685,6 +685,15 @@ impl<'a> AstValidator<'a> { }); } + if let Some(coroutine_kind) = sig.header.coroutine_kind { + self.dcx().emit_err(errors::CoroutineAndCVariadic { + spans: vec![coroutine_kind.span(), variadic_param.span], + coroutine_kind: coroutine_kind.as_str(), + coroutine_span: coroutine_kind.span(), + variadic_span: variadic_param.span, + }); + } + match fn_ctxt { FnCtxt::Foreign => return, FnCtxt::Free => match sig.header.ext { diff --git a/compiler/rustc_ast_passes/src/errors.rs b/compiler/rustc_ast_passes/src/errors.rs index 476ed27a10e..f8806ef21c1 100644 --- a/compiler/rustc_ast_passes/src/errors.rs +++ b/compiler/rustc_ast_passes/src/errors.rs @@ -660,6 +660,18 @@ pub(crate) struct ConstAndCVariadic { } #[derive(Diagnostic)] +#[diag(ast_passes_coroutine_and_c_variadic)] +pub(crate) struct CoroutineAndCVariadic { + #[primary_span] + pub spans: Vec<Span>, + pub coroutine_kind: &'static str, + #[label(ast_passes_const)] + pub coroutine_span: Span, + #[label(ast_passes_variadic)] + pub variadic_span: Span, +} + +#[derive(Diagnostic)] #[diag(ast_passes_pattern_in_foreign, code = E0130)] // FIXME: deduplicate with rustc_lint (`BuiltinLintDiag::PatternsInFnsWithoutBody`) pub(crate) struct PatternInForeign { diff --git a/tests/ui/c-variadic/not-async.rs b/tests/ui/c-variadic/not-async.rs new file mode 100644 index 00000000000..45a7e1f8972 --- /dev/null +++ b/tests/ui/c-variadic/not-async.rs @@ -0,0 +1,7 @@ +//@ edition: 2021 +#![feature(c_variadic)] +#![crate_type = "lib"] + +async unsafe extern "C" fn cannot_be_async(x: isize, ...) {} +//~^ ERROR functions cannot be both `async` and C-variadic +//~| ERROR hidden type for `impl Future<Output = ()>` captures lifetime that does not appear in bounds diff --git a/tests/ui/c-variadic/not-async.stderr b/tests/ui/c-variadic/not-async.stderr new file mode 100644 index 00000000000..b8caf0d8bd8 --- /dev/null +++ b/tests/ui/c-variadic/not-async.stderr @@ -0,0 +1,19 @@ +error: functions cannot be both `async` and C-variadic + --> $DIR/not-async.rs:5:1 + | +LL | async unsafe extern "C" fn cannot_be_async(x: isize, ...) {} + | ^^^^^ `async` because of this ^^^ C-variadic because of this + +error[E0700]: hidden type for `impl Future<Output = ()>` captures lifetime that does not appear in bounds + --> $DIR/not-async.rs:5:59 + | +LL | async unsafe extern "C" fn cannot_be_async(x: isize, ...) {} + | --------------------------------------------------------- ^^ + | | + | opaque type defined here + | + = note: hidden type `{async fn body of cannot_be_async()}` captures lifetime `'_` + +error: aborting due to 2 previous errors + +For more information about this error, try `rustc --explain E0700`. diff --git a/tests/ui/inference/note-and-explain-ReVar-124973.rs b/tests/ui/inference/note-and-explain-ReVar-124973.rs index f1e24645636..aa4b909fa76 100644 --- a/tests/ui/inference/note-and-explain-ReVar-124973.rs +++ b/tests/ui/inference/note-and-explain-ReVar-124973.rs @@ -3,6 +3,7 @@ #![feature(c_variadic)] async unsafe extern "C" fn multiple_named_lifetimes<'a, 'b>(_: u8, ...) {} -//~^ ERROR hidden type for `impl Future<Output = ()>` captures lifetime that does not appear in bounds +//~^ ERROR functions cannot be both `async` and C-variadic +//~| ERROR hidden type for `impl Future<Output = ()>` captures lifetime that does not appear in bounds fn main() {} diff --git a/tests/ui/inference/note-and-explain-ReVar-124973.stderr b/tests/ui/inference/note-and-explain-ReVar-124973.stderr index 574f6508e4c..964fbc4a4fb 100644 --- a/tests/ui/inference/note-and-explain-ReVar-124973.stderr +++ b/tests/ui/inference/note-and-explain-ReVar-124973.stderr @@ -1,3 +1,9 @@ +error: functions cannot be both `async` and C-variadic + --> $DIR/note-and-explain-ReVar-124973.rs:5:1 + | +LL | async unsafe extern "C" fn multiple_named_lifetimes<'a, 'b>(_: u8, ...) {} + | ^^^^^ `async` because of this ^^^ C-variadic because of this + error[E0700]: hidden type for `impl Future<Output = ()>` captures lifetime that does not appear in bounds --> $DIR/note-and-explain-ReVar-124973.rs:5:73 | @@ -8,6 +14,6 @@ LL | async unsafe extern "C" fn multiple_named_lifetimes<'a, 'b>(_: u8, ...) {} | = note: hidden type `{async fn body of multiple_named_lifetimes<'a, 'b>()}` captures lifetime `'_` -error: aborting due to 1 previous error +error: aborting due to 2 previous errors For more information about this error, try `rustc --explain E0700`. |
